Skip to content

Commit

Permalink
fix(export): sanitize any html that could exist in header titles
Browse files Browse the repository at this point in the history
- also fix a number cell format in Excel export
  • Loading branch information
ghiscoding committed Nov 15, 2021
1 parent 76cee09 commit abdae52
Show file tree
Hide file tree
Showing 5 changed files with 26 additions and 17 deletions.
12 changes: 10 additions & 2 deletions examples/webpack-demo-vanilla-bundle/src/examples/example16.ts
Expand Up @@ -3,14 +3,14 @@ import {
Column,
Editors,
FieldType,
FileType,
Filters,
Formatters,
GridOption,
OperatorType,
} from '@slickgrid-universal/common';
import { SlickCustomTooltip } from '@slickgrid-universal/custom-tooltip-plugin';
import { ExcelExportService } from '@slickgrid-universal/excel-export';
import { TextExportService } from '@slickgrid-universal/text-export';
import { Slicker, SlickVanillaGridBundle } from '@slickgrid-universal/vanilla-bundle';

import { ExampleGridOptions } from './example-grid-options';
Expand Down Expand Up @@ -98,6 +98,7 @@ export class Example16 {
minLength: 5,
maxLength: 255,
},
exportWithFormatter: false,
formatter: (row, cell, value, column, dataContext) => `<span title="regular tooltip (from title attribute)\r${dataContext.title} cell value:\r${value || ''}">${value || ''}</span>`,
// define tooltip options here OR for the entire grid via the grid options (cell tooltip options will have precedence over grid options)
customTooltip: {
Expand All @@ -113,6 +114,7 @@ export class Example16 {
minLength: 5,
maxLength: 255,
},
exportWithFormatter: false,
formatter: (row, cell, value, column, dataContext) => `<span title="regular tooltip (from title attribute)\r${dataContext.title} cell value:\r\r${value || ''}">${value || ''}</span>`,
// define tooltip options here OR for the entire grid via the grid options (cell tooltip options will have precedence over grid options)
customTooltip: {
Expand All @@ -128,6 +130,7 @@ export class Example16 {
width: 90,
sortable: true,
filterable: true,
exportWithFormatter: false,
// filter: { model: Filters.compoundInput },
// formatter: Formatters.dollar,
formatter: Formatters.multiple,
Expand All @@ -147,6 +150,7 @@ export class Example16 {
maxValue: 100,
// params: { hideSliderNumber: true },
},
exportWithFormatter: false,
formatter: Formatters.percentCompleteBar,
sortable: true, filterable: true,
filter: { model: Filters.slider, operator: '>=' },
Expand Down Expand Up @@ -315,8 +319,12 @@ export class Example16 {
excelExportOptions: {
exportWithFormatter: true
},
enableTextExport: true,
textExportOptions: {
exportWithFormatter: true
},
// Custom Tooltip options can be defined in a Column or Grid Options or a mixed of both (first options found wins)
registerExternalResources: [new SlickCustomTooltip(), new ExcelExportService()],
registerExternalResources: [new SlickCustomTooltip(), new ExcelExportService(), new TextExportService()],
customTooltip: {
formatter: this.tooltipFormatter.bind(this),
headerFormatter: this.headerFormatter,
Expand Down
4 changes: 2 additions & 2 deletions packages/excel-export/package.json
Expand Up @@ -49,12 +49,12 @@
],
"dependencies": {
"@slickgrid-universal/common": "^0.19.0",
"excel-builder-webpacker": "^2.1.5",
"excel-builder-webpacker": "^2.1.6",
"moment-mini": "^2.24.0"
},
"devDependencies": {
"cross-env": "^7.0.3",
"npm-run-all": "^4.1.5",
"rimraf": "^3.0.2"
}
}
}
7 changes: 4 additions & 3 deletions packages/excel-export/src/excelExport.service.ts
Expand Up @@ -210,7 +210,7 @@ export class ExcelExportService implements ExternalResource, BaseExcelExportServ
} else {
// this trick will generate a temp <a /> tag
// the code will then trigger a hidden click for it to start downloading
const link = document && document.createElement('a');
const link = document.createElement('a');
const url = URL.createObjectURL(options.blob);

if (link && document) {
Expand Down Expand Up @@ -267,7 +267,8 @@ export class ExcelExportService implements ExternalResource, BaseExcelExportServ
}
break;
case FieldType.number:
const val = isNaN(+data) ? null : +data;
const num = parseFloat(data as string);
const val = isNaN(num) ? null : num;
outputData = { value: val, metadata: { style: this._stylesheetFormats.numberFormatter.id } };
break;
default:
Expand Down Expand Up @@ -374,7 +375,7 @@ export class ExcelExportService implements ExternalResource, BaseExcelExportServ
this._columnHeaders = this.getColumnHeaders(columns) || [];
if (this._columnHeaders && Array.isArray(this._columnHeaders) && this._columnHeaders.length > 0) {
// add the header row + add a new line at the end of the row
outputHeaderTitles = this._columnHeaders.map((header) => ({ value: header.title, metadata }));
outputHeaderTitles = this._columnHeaders.map((header) => ({ value: sanitizeHtmlToText(header.title), metadata }));
}

// do we have a Group by title?
Expand Down
2 changes: 1 addition & 1 deletion packages/text-export/src/textExport.service.ts
Expand Up @@ -228,7 +228,7 @@ export class TextExportService implements ExternalResource, BaseTextExportServic
this._columnHeaders = this.getColumnHeaders(columns) || [];
if (this._columnHeaders && Array.isArray(this._columnHeaders) && this._columnHeaders.length > 0) {
// add the header row + add a new line at the end of the row
const outputHeaderTitles = this._columnHeaders.map((header) => `${this._exportQuoteWrapper}${header.title}${this._exportQuoteWrapper}`);
const outputHeaderTitles = this._columnHeaders.map((header) => sanitizeHtmlToText(`${this._exportQuoteWrapper}${header.title}${this._exportQuoteWrapper}`));
outputDataString += (outputHeaderTitles.join(this._delimiter) + this._lineCarriageReturn);
}

Expand Down
18 changes: 9 additions & 9 deletions yarn.lock
Expand Up @@ -4840,12 +4840,12 @@ events@^3.2.0:
resolved "https://registry.yarnpkg.com/events/-/events-3.3.0.tgz#31a95ad0a924e2d2c419a813aeb2c4e878ea7400"
integrity sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==

excel-builder-webpacker@^2.1.5:
version "2.1.5"
resolved "https://registry.yarnpkg.com/excel-builder-webpacker/-/excel-builder-webpacker-2.1.5.tgz#8e5c8c40bbad5f31b9ee3ed6b657453caeba8986"
integrity sha512-78n0Qci3GmmrQY8eiTdcMm0VA66QI5dykXDLyWFt8KzpqF9nYnOYreiYSc5I2UftBrv095qdOZ0rCvR3bO8hsg==
excel-builder-webpacker@^2.1.6:
version "2.1.6"
resolved "https://registry.yarnpkg.com/excel-builder-webpacker/-/excel-builder-webpacker-2.1.6.tgz#7d318f5c25a6d60db0986778e13d01fbdb267825"
integrity sha512-hHhZ+NgzuZ6TLltDgLtNNIRXn1vToEh4TwjWkwNDDq35qjo8Dlt2Vhm7VZr1Tf76hNesyMKg0IlmahsXkYqHYw==
dependencies:
jszip "3.5.0"
jszip "^3.7.1"
lodash "^4.17.21"
q "^1.5.1"

Expand Down Expand Up @@ -7590,10 +7590,10 @@ jsprim@^1.2.2:
json-schema "0.2.3"
verror "1.10.0"

jszip@3.5.0:
version "3.5.0"
resolved "https://registry.yarnpkg.com/jszip/-/jszip-3.5.0.tgz#b4fd1f368245346658e781fec9675802489e15f6"
integrity sha512-WRtu7TPCmYePR1nazfrtuF216cIVon/3GWOvHS9QR5bIwSbnxtdpma6un3jyGGNhHsKCSzn5Ypk+EkDRvTGiFA==
jszip@^3.7.1:
version "3.7.1"
resolved "https://registry.yarnpkg.com/jszip/-/jszip-3.7.1.tgz#bd63401221c15625a1228c556ca8a68da6fda3d9"
integrity sha512-ghL0tz1XG9ZEmRMcEN2vt7xabrDdqHHeykgARpmZ0BiIctWxM47Vt63ZO2dnp4QYt/xJVLLy5Zv1l/xRdh2byg==
dependencies:
lie "~3.3.0"
pako "~1.0.2"
Expand Down

0 comments on commit abdae52

Please sign in to comment.