diff --git a/packages/analytics/addon/components/ca-report-preview.hbs b/packages/analytics/addon/components/ca-report-preview.hbs index 22a97df6d..3bec1abbd 100644 --- a/packages/analytics/addon/components/ca-report-preview.hbs +++ b/packages/analytics/addon/components/ca-report-preview.hbs @@ -4,7 +4,16 @@ {{else}} - + + {{t "caluma.analytics.preview.export"}} + +
{{#each this.data.value.headings as |header|}} diff --git a/packages/analytics/addon/components/ca-report-preview.js b/packages/analytics/addon/components/ca-report-preview.js index 57a0fcb84..0ffd33a9f 100644 --- a/packages/analytics/addon/components/ca-report-preview.js +++ b/packages/analytics/addon/components/ca-report-preview.js @@ -1,9 +1,12 @@ +import { action } from "@ember/object"; +import { next } from "@ember/runloop"; import { inject as service } from "@ember/service"; import Component from "@glimmer/component"; import { tracked } from "@glimmer/tracking"; import { queryManager } from "ember-apollo-client"; import { task } from "ember-concurrency"; import { trackedTask } from "reactiveweb/ember-concurrency"; +import * as XLSX from "xlsx"; import getAnalyticsResultsQuery from "@projectcaluma/ember-analytics/gql/queries/get-analytics-results.graphql"; @@ -58,4 +61,17 @@ export default class CaReportPreviewComponent extends Component { } return null; } + + @action + exportTable() { + next(() => { + const wb = XLSX.utils.table_to_book( + document.getElementById("reports-table"), + ); + XLSX.writeFile( + wb, + `${new Date().toLocaleDateString()}_${this.args.slug}.xlsx`, + ); + }); + } } diff --git a/packages/analytics/package.json b/packages/analytics/package.json index d4cd05da3..590f36598 100644 --- a/packages/analytics/package.json +++ b/packages/analytics/package.json @@ -35,7 +35,8 @@ "ember-uikit": "^9.1.1", "ember-validated-form": "^7.0.1", "graphql": "^15.8.0", - "reactiveweb": "^1.2.2" + "reactiveweb": "^1.2.2", + "xlsx": "https://cdn.sheetjs.com/xlsx-0.20.2/xlsx-0.20.2.tgz" }, "//": [ "TODO: remove obsolete dependency to `ember-data` which is only necessary", diff --git a/packages/analytics/tests/integration/components/ca-report-preview-test.js b/packages/analytics/tests/integration/components/ca-report-preview-test.js index a08caaec5..c4c4d03dc 100644 --- a/packages/analytics/tests/integration/components/ca-report-preview-test.js +++ b/packages/analytics/tests/integration/components/ca-report-preview-test.js @@ -9,14 +9,11 @@ module("Integration | Component | ca-report-preview", function (hooks) { setupRenderingTest(hooks); setupIntl(hooks); - test.skip("it renders", async function (assert) { + test("it renders", async function (assert) { await render(hbs``); - assert - .dom(this.element) - .hasText( - "t:caluma.analytics.sections.table-preview:() t:caluma.analytics.preview.refresh:() t:caluma.analytics.preview.download:()", - ); + assert.dom(this.element).hasText("t:caluma.analytics.preview.export:()"); + assert.dom(this.element.querySelector("#reports-table")).exists(); }); todo("it renders table data", async function () {}); diff --git a/packages/analytics/translations/de.yaml b/packages/analytics/translations/de.yaml index 4b6b7aab8..1be7a0148 100644 --- a/packages/analytics/translations/de.yaml +++ b/packages/analytics/translations/de.yaml @@ -48,3 +48,5 @@ caluma: cases: Dossiers work-items: Aufgaben documents: Dokumente + preview: + export: Export diff --git a/packages/analytics/translations/en.yaml b/packages/analytics/translations/en.yaml index c117350de..dbae58a5c 100644 --- a/packages/analytics/translations/en.yaml +++ b/packages/analytics/translations/en.yaml @@ -48,3 +48,5 @@ caluma: cases: Cases work-items: Work items documents: Documents + preview: + export: Export diff --git a/packages/analytics/translations/fr.yaml b/packages/analytics/translations/fr.yaml index 72049c061..9dbff2288 100644 --- a/packages/analytics/translations/fr.yaml +++ b/packages/analytics/translations/fr.yaml @@ -48,3 +48,5 @@ caluma: cases: Dossiers work-items: Tâches documents: Documents + preview: + export: Export diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 06c23ec18..e985eb94e 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -103,7 +103,7 @@ importers: version: 16.3.1 stylelint-config-standard-scss: specifier: 13.0.0 - version: 13.0.0(postcss@8.4.35)(stylelint@16.3.1) + version: 13.0.0(postcss@8.4.38)(stylelint@16.3.1) stylelint-prettier: specifier: ^5.0.0 version: 5.0.0(prettier@3.2.5)(stylelint@16.3.1) @@ -374,6 +374,9 @@ importers: reactiveweb: specifier: ^1.2.2 version: 1.2.2(@babel/core@7.24.3)(@ember/test-waiters@3.1.0)(@glimmer/component@1.1.2)(@glimmer/tracking@1.1.2)(@glint/template@1.3.0)(ember-source@5.7.0) + xlsx: + specifier: https://cdn.sheetjs.com/xlsx-0.20.2/xlsx-0.20.2.tgz + version: '@cdn.sheetjs.com/xlsx-0.20.2/xlsx-0.20.2.tgz' devDependencies: '@ember/optional-features': specifier: 2.1.0 @@ -653,7 +656,7 @@ importers: version: file:packages/core(@glimmer/component@1.1.2)(@glint/template@1.3.0)(ember-data@5.3.3)(ember-resources@7.0.0)(ember-source@5.7.0)(webpack@5.91.0) '@projectcaluma/ember-form': specifier: workspace:^ - version: file:packages/form(@ember/test-waiters@3.1.0)(@glint/template@1.3.0)(@projectcaluma/ember-workflow@12.11.0)(ember-resources@7.0.0)(ember-source@5.7.0)(webpack@5.91.0) + version: file:packages/form(@ember/test-waiters@3.1.0)(@glint/template@1.3.0)(@projectcaluma/ember-workflow@12.11.1)(ember-resources@7.0.0)(ember-source@5.7.0)(webpack@5.91.0) '@projectcaluma/ember-workflow': specifier: workspace:^ version: file:packages/workflow(@ember/test-waiters@3.1.0)(@glimmer/tracking@1.1.2)(@glint/template@1.3.0)(ember-resources@7.0.0)(ember-source@5.7.0)(webpack@5.91.0) @@ -17069,6 +17072,15 @@ packages: postcss: 8.4.35 dev: true + /postcss-scss@4.0.9(postcss@8.4.38): + resolution: {integrity: sha512-AjKOeiwAitL/MXxQW2DliT28EKukvvbEWx3LBmJIRN8KfBGZbRTxNYW0kSqi1COiTZ57nZ9NW06S6ux//N1c9A==} + engines: {node: '>=12.0'} + peerDependencies: + postcss: ^8.4.29 + dependencies: + postcss: 8.4.38 + dev: true + /postcss-selector-parser@6.0.15: resolution: {integrity: sha512-rEYkQOMUCEMhsKbK66tbEU9QVIxbhN18YiniAwA7XQYTVBqrBy+P2p5JcdqsHgKM2zWylp8d7J6eszocfds5Sw==} engines: {node: '>=4'} @@ -18840,7 +18852,7 @@ packages: resolution: {integrity: sha512-DU2KZiB6VbPkO2tGSqQ9n96ZstUPjW7X4sGO6V2m1myIQluX0p1Ol8BrA/l6/EesqhMqXOIXs3cJNOy1UuU2BA==} dev: true - /stylelint-config-recommended-scss@14.0.0(postcss@8.4.35)(stylelint@16.3.1): + /stylelint-config-recommended-scss@14.0.0(postcss@8.4.38)(stylelint@16.3.1): resolution: {integrity: sha512-HDvpoOAQ1RpF+sPbDOT2Q2/YrBDEJDnUymmVmZ7mMCeNiFSdhRdyGEimBkz06wsN+HaFwUh249gDR+I9JR7Onw==} engines: {node: '>=18.12.0'} peerDependencies: @@ -18850,8 +18862,8 @@ packages: postcss: optional: true dependencies: - postcss: 8.4.35 - postcss-scss: 4.0.9(postcss@8.4.35) + postcss: 8.4.38 + postcss-scss: 4.0.9(postcss@8.4.38) stylelint: 16.3.1 stylelint-config-recommended: 14.0.0(stylelint@16.3.1) stylelint-scss: 6.2.1(stylelint@16.3.1) @@ -18866,7 +18878,7 @@ packages: stylelint: 16.3.1 dev: true - /stylelint-config-standard-scss@13.0.0(postcss@8.4.35)(stylelint@16.3.1): + /stylelint-config-standard-scss@13.0.0(postcss@8.4.38)(stylelint@16.3.1): resolution: {integrity: sha512-WaLvkP689qSYUpJQPCo30TFJSSc3VzvvoWnrgp+7PpVby5o8fRUY1cZcP0sePZfjrFl9T8caGhcKg0GO34VDiQ==} engines: {node: '>=18.12.0'} peerDependencies: @@ -18876,9 +18888,9 @@ packages: postcss: optional: true dependencies: - postcss: 8.4.35 + postcss: 8.4.38 stylelint: 16.3.1 - stylelint-config-recommended-scss: 14.0.0(postcss@8.4.35)(stylelint@16.3.1) + stylelint-config-recommended-scss: 14.0.0(postcss@8.4.38)(stylelint@16.3.1) stylelint-config-standard: 36.0.0(stylelint@16.3.1) dev: true @@ -20447,6 +20459,14 @@ packages: /zen-observable@0.8.15: resolution: {integrity: sha512-PQ2PC7R9rslx84ndNBZB/Dkv8V8fZEpk83RLgXtYd0fwUgEjseMn1Dgajh2x6S8QbZAFa9p2qVCEuYZNgve0dQ==} + '@cdn.sheetjs.com/xlsx-0.20.2/xlsx-0.20.2.tgz': + resolution: {tarball: https://cdn.sheetjs.com/xlsx-0.20.2/xlsx-0.20.2.tgz} + name: xlsx + version: 0.20.2 + engines: {node: '>=0.8'} + hasBin: true + dev: false + file:packages/core(@glimmer/component@1.1.2)(@glint/template@1.3.0)(ember-data@5.3.3)(ember-resources@7.0.0)(ember-source@5.7.0)(webpack@5.91.0): resolution: {directory: packages/core, type: directory} id: file:packages/core @@ -20496,7 +20516,7 @@ packages: - typescript - webpack - file:packages/form(@ember/test-waiters@3.1.0)(@glint/template@1.3.0)(@projectcaluma/ember-workflow@12.11.0)(ember-resources@7.0.0)(ember-source@5.7.0)(webpack@5.91.0): + file:packages/form(@ember/test-waiters@3.1.0)(@glint/template@1.3.0)(@projectcaluma/ember-workflow@12.11.1)(ember-resources@7.0.0)(ember-source@5.7.0)(webpack@5.91.0): resolution: {directory: packages/form, type: directory} id: file:packages/form name: '@projectcaluma/ember-form'