mirror of
https://github.com/ever-co/ever-gauzy.git
synced 2026-10-02 01:54:50 +08:00
* fix(security): neutralize spreadsheet formulas in CSV exports GHSA-7xp5-j564-4752 (medium): exported cells were written verbatim, so a stored value beginning with = + - or @ executed as a formula when a colleague opened the export in Excel or Sheets. A shared encoder in @gauzy/utils prefixes an apostrophe to any cell starting with a formula trigger (including the full-width forms), leaves strictly numeric values alone, and is reversed on import so an export/import round-trip stays byte-exact. Every field is now quoted, which also stops a bare CR inside a value from starting a new spreadsheet row, and the invoice CSV in the web app gets real RFC 4180 quoting instead of JSON.stringify. GHSA-86mw-2crg-vmhc residuals (low): the public invite routes are throttled, the shipped compose files no longer trust a forwarded client IP while publishing the API port directly, and RequestContext.currentIp() resolves the client address the same way the throttler does instead of reading a spoofable header. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> * chore(cspell): add the new vocabulary and use US spellings Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> * fix(export-import): decode CSV cells only for archives we marked The import side reversed the spreadsheet-formula escape on every parsed row, but an uploaded ZIP is not necessarily one this server wrote: it can be a dump from an older Gauzy, a filled-in `/export/template`, or a CSV set built by external tooling. For those, un-escaping is data loss — a legitimate value such as `'=notes` was persisted as `=notes`, silently. Both review bots flagged this as the one thing blocking the merge, and they were right: the decoder had no way to tell "we escaped this" from "somebody else wrote this". A data export now carries a `gauzy-export.json` marker at the archive root (format, version, `spreadsheetSafeCells`), written by `exportTables` and `exportSpecificTables`. `ImportService` resolves that marker once per import and decodes rows only when it is present and recognized; anything else is imported byte for byte as it was parsed. `/export/template` is deliberately NOT marked — an operator fills it in by hand, so nothing in it was ever escaped. The manifest reader is defensive about an attacker-supplied file: missing, oversized, malformed, a foreign format or a newer version all mean "do not decode". The invoice/payment CSV builder no longer has a path that skips encoding: a pre-joined header line used to be written through verbatim, and it was the only value in the file that reached disk unquoted and un-neutralized. `buildCsv` and `generateCsv` now declare `headers: string[]` (both callers already pass one), and a stray string from an untyped caller is split and encoded rather than trusted. Tests: `import.service.spec.ts` imports the same escaped CSV with and without a marker and asserts the apostrophe survives when unmarked (reverting the gate fails those 5 tests); `export.service.spec.ts` asserts the data archive carries the marker and the template archive does not. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5 <noreply@anthropic.com>
@gauzy/utils
This library was generated with Nx.
Description
@gauzy/utils is a collection of common utility functions for streamlined development in JavaScript and TypeScript. It is designed for use across various frameworks, including Angular, NestJS, or any TypeScript-based environment.
Installation
Install the package via npm or yarn:
npm install @gauzy/utils
# or
yarn add @gauzy/utils
Build
Run nx build utils to build the library. The build artifacts will be stored in the dist/ directory.
Publishing
After building your library with nx build utils, go to the dist folder cd dist/utils and run npm publish.
Running unit tests
Run nx test utils to execute the unit tests via Jest.