# Security Threat Model: Apache ECharts (AppSheet Fork)

## Asset Definition & Scope

-   **Component:** Apache ECharts — client-side JavaScript/TypeScript charting
    and data-visualization library (AppSheet fork)
-   **Repository:** Git-on-Borg
    (`https://gnocchi-internal.googlesource.com/third_party/echarts`, branch
    `main`). Mirrored as `appsheet-third-party/echarts`, which is the URL
    actually resolved by `Nirvana/Content/package.json`.
-   **Upstream version:** Apache ECharts `5.4.0` (upstream commit
    `cb722aecad5b44476a5c2f4c343b699cfa834b0e`, per `METADATA`;
    `last_upgrade_date` 2022-11-16). Declared in `package.json` and
    `src/core/echarts.ts:version`.
-   **Runtime dependency:** `zrender` pinned to a pre-release nightly
    (`npm:zrender-nightly@^5.4.1-dev.20221104`) rather than a stable release.
-   **Scope:** Browser-side rendering library bundled into the AppSheet web
    frontend (`jeenee/Nirvana/Content`). It renders bar, line, area, pie,
    doughnut, scatter, KPI and graph charts for (a) end-user-facing AppSheet
    application chart views and (b) the AppSheet Admin Console. Scope covers the
    TypeScript sources under `src/` **and** the pre-built bundles checked into
    `dist/`, which are shipped to browsers.
-   **Fork delta:** The fork consists of a squashed upstream import plus four
    commits (`4e53257`, `1bd413c`, `60d53ba`, `967afa1`), all of which modify
    `src/component/tooltip/TooltipHTMLContent.ts` (and regenerated `dist/`
    bundles) to suppress **Trusted Types** enforcement violations. No upstream
    security patches have been backported.

## Prioritization Signals

-   **1P OSS:** No (Third-party Apache-licensed OSS maintained as an internal
    customized fork for Google AppSheet)
-   **1P Proprietary Shipped Software:** Yes (Compiled and minified into the
    AppSheet frontend JavaScript bundles served to every AppSheet user's
    browser; `dist/*.min.js` artifacts are committed to this repository)
-   **High-Risk Code Surface:** Yes (Client-side rendering engine that
    interpolates caller-supplied strings into `innerHTML`, contains an
    intentionally **pass-through Trusted Types policy** added by the fork,
    performs dynamic code evaluation via `new Function` in GeoJSON parsing, and
    writes unvalidated CSS into inline `style` attributes)
-   **Perimeter Exposure:** Yes (Executes in the browsers of public Internet
    users of AppSheet applications and in the AppSheet Admin Console; AppSheet
    is a 1P service exposed to the public Internet and to customers)
-   **Data Sensitivity:** High (Renders customer business records — the row
    values, column display names, app names, and creator email addresses that
    flow into chart series, axis categories, labels, and tooltips are customer
    business data and PII, displayed client-side)
-   **Untrusted Input Handling:** Yes (Two distinct untrusted sources: **chart
    configuration authored by AppSheet app creators** — chart type, column
    display names, aggregations, titles — and **record data entered by
    application end users**, both of which reach label and tooltip rendering
    paths)
-   **Business Value:** ECharts is the sole charting engine behind AppSheet
    chart views and the Admin Console dashboards. A DOM-XSS defect in a tooltip
    or label sink executes attacker JavaScript in the AppSheet origin, enabling
    session theft, cross-tenant data access, and privilege escalation against
    app creators and Admin Console operators. The fork's deliberate weakening of
    Trusted Types removes a defense-in-depth control that would otherwise
    mitigate exactly this class of bug.

## Scanning Harness Prompts

1.  **Pass-through Trusted Types policies (fork-introduced, highest priority).**
    `TooltipHTMLContent.setContent` creates Trusted Types policies named
    `TooltipHTMLFix1`, `TooltipHTMLFix2`, and `TooltipHTMLFix3`. `TooltipHTMLFix2`
    is defined as `createHTML: (string) => string` — an identity function that
    launders arbitrary strings into `TrustedHTML` and assigns them to
    `el.innerHTML`. Treat this as a **Trusted Types bypass**, not a fix: it
    converts a browser-enforced XSS guardrail into a no-op while satisfying the
    violation reporter. Flag every string reaching this sink. Also flag that
    `createPolicy` is invoked on **every** `setContent` call (i.e. on every
    tooltip render) rather than once at module init — under a CSP
    `trusted-types` allow-list without `allow-duplicates` this throws a
    `TypeError` on the second call, and it is an unbounded policy-creation hot
    path.
2.  **Tooltip formatter → `innerHTML` data flow.** Trace
    `TooltipView.prototype._showTooltipContent` → `tooltipContent.setContent` →
    `TooltipHTMLContent.setContent` → `el.innerHTML`. Note the asymmetry: a
    **string** `formatter` has its `{a}/{b}/{c}` placeholders escaped via
    `formatTpl(html, params, true)` → `encodeHTML`, but the template shell
    itself is raw HTML; a **function** `formatter` return value is inserted with
    **no escaping whatsoever**. The default (no-formatter) markup path in
    `src/component/tooltip/tooltipMarkup.ts` does apply `encodeHTML` to names
    and values and is the safe baseline — verify no regression there.
3.  **CSS injection via `extraCssText`.** In `TooltipHTMLContent.prototype.show`,
    `tooltipModel.get('extraCssText')` is concatenated raw into
    `el.style.cssText` with no validation or delimiter escaping. Check for
    injection of additional CSS declarations, and for exfiltration primitives
    such as `background:url(...)` attribute selectors.
4.  **Dynamic code evaluation in GeoJSON parsing.**
    `src/coord/geo/GeoJSONResource.ts:parseInput` falls back to
    `new Function('return (' + source + ');')()` when `JSON.parse` is
    unavailable. Confirm this fallback is unreachable in supported browsers and
    that `registerMap` callers never pass attacker-controlled strings; any reach
    is direct arbitrary JavaScript execution.
5.  **Unprotected `innerHTML` / `document.write` sinks outside the tooltip.**
    The fork patched *only* the tooltip. Audit the following, none of which are
    wrapped in a Trusted Types policy and all of which will hard-fail or bypass
    under TT enforcement:
    -   `src/component/toolbox/feature/DataView.ts` — `header.innerHTML` from
        `lang[0] || model.get('title')`, `viewMain.innerHTML = htmlOrDom` from
        the caller-supplied `optionToContent` callback, and
        `closeButton.innerHTML` / `refreshButton.innerHTML` from `lang`.
    -   `src/component/toolbox/feature/SaveAsImage.ts` —
        `tab.document.write(html)` and `doc.write(bstr)` build markup by string
        concatenation, interpolating `url` and `lang[0]` into an `<img
        src=... title=...>` attribute context.
    -   `src/core/echarts.ts` — `getSvgRoot().innerHTML = content` in the
        connected-charts SVG export path.
    -   `TooltipHTMLContent.setContent` — `arrowEl.innerHTML = arrow` in the
        `HTMLElement[]` content branch is **not** routed through any policy,
        unlike the sibling string branch.
6.  **Build-artifact divergence between `src/` and `dist/` (supply-chain
    integrity).** The committed bundles are inconsistent with each other and
    with the sources — see the table under *Privileged Actions*.
    `dist/echarts.simple.js` / `.simple.min.js` contain **none** of the fork
    patches, and `dist/echarts.esm.js` / `.esm.min.js` are stale at the
    `4e53257` state (only the empty-clear `TooltipHTMLFix1` policy; missing the
    `TooltipHTMLFix2` string-content path). Verify which artifact AppSheet
    actually ships and whether `dist/` can be reproduced from `src/`.
7.  **Rich-text template token injection.** Label `formatter` values that return
    ECharts rich-text markup (`{styleName|text}`) interpolate data values into
    the template. Unescaped `{`, `}`, or `|` characters in a data value can
    break out of the intended token and select a different `rich` style. This is
    canvas/SVG-rendered rather than an HTML sink, so treat it as a UI-spoofing
    and rendering-integrity issue rather than XSS.
8.  **Missing upstream security patches.** The fork has not been rebased since
    2022-11-16. Enumerate Apache ECharts and `zrender` advisories affecting
    `5.4.0` and the `zrender-nightly@5.4.1-dev.20221104` pre-release, and check
    whether each fix is absent here.

## Entry Points and Untrusted Inputs

All entry points are library APIs invoked by AppSheet frontend code; the library
performs no authentication of its own.

| Entry Point | Type | Trusted? | Validation |
|---|---|---|---|
| `echartsInstance.setOption(option)` — the primary API; receives the full chart config | Public API / config object | No | No schema validation or sanitization; option values are mapped onto component models and rendered |
| `tooltip.formatter` (function) — e.g. `ChartView.tsx`, `bar_chart_builder.ts`, `scatter_chart_builder.ts` | Callback returning HTML | No | **None.** Return value flows to `el.innerHTML` via the pass-through TT policy |
| `tooltip.formatter` (string template) | HTML template with `{a}/{b}/{c}` | No | Placeholders escaped by `formatTpl(..., encode=true)` → `encodeHTML`; the surrounding template is raw HTML |
| Default tooltip markup (no `formatter`) | Internal markup builder | No | `tooltipMarkup.ts` applies `encodeHTML` to series names and values — safe baseline |
| `tooltip.extraCssText` | Raw CSS string | No | **None.** Concatenated directly into `el.style.cssText` |
| `series.label.formatter` / `axisLabel.formatter` / legend formatter | String or callback | No | Rendered as canvas/SVG text, not HTML; rich-text `{style|text}` tokens are parsed without escaping data values |
| `series[].name`, `series.data[].name`, `xAxis.data[]`, `title.text` | Config strings sourced from customer data | No | Escaped in the default tooltip path; passed verbatim into custom formatters |
| `graphic` component elements | zrender shape descriptors | No | Rendered via zrender (canvas/SVG), not HTML. `type: 'image'` accepts an arbitrary `style.image` URL → outbound request from the AppSheet origin |
| `echarts.registerMap(name, geoJson)` | GeoJSON object or string | No | `GeoJSONResource.parseInput` uses `JSON.parse`, falling back to `new Function(...)` |
| `toolbox.dataView.optionToContent` | Callback returning HTML/DOM | No | **None.** String return assigned to `viewMain.innerHTML` |
| `echarts.registerTheme(name, theme)` — used by `ChartView.tsx` (`darkTheme()`) | Theme object | Yes | First-party static theme definition |

## Trust Boundaries and Auth Assumptions

-   **Authentication**: None at the library level. ECharts runs entirely in the
    browser and authenticates nothing. All authentication is performed upstream
    by AppSheet before chart data is delivered to the client.
-   **Authorization**: None at the library level. Row-level and table-level
    access control is enforced by the AppSheet backend and the AppSheet security
    filter model before rows reach `queryRowValues` and are passed into chart
    options.
-   **Implicit trust**: The library implicitly treats **every string in the
    option object as trusted, renderable markup**. This assumption is invalid in
    AppSheet, where option strings are assembled from two untrusted sources:
    app-creator-authored view configuration (column display names, titles,
    aggregations) and end-user-entered record values.
-   **Trusted Types**: The AppSheet frontend runs under a Trusted Types policy.
    The fork's patches satisfy that policy **without** providing sanitization;
    the browser guardrail that would otherwise block tooltip DOM-XSS is
    intentionally neutralized for this code path. Any XSS analysis must assume
    Trusted Types provides **no** protection for ECharts tooltips.
-   **Same-origin blast radius**: Charts render in the main AppSheet document,
    not a sandboxed iframe. Script execution in a chart tooltip runs with full
    AppSheet origin privileges (session cookies, `localStorage`, in-page APIs).
-   **Boundary crossings**: App-creator view definition **and** end-user record
    data → AppSheet backend → AppSheet frontend (`ChartView.tsx`, chart option
    builders) → ECharts option object → tooltip/label rendering → browser DOM.
    The critical crossing is the last one, where data leaves the React-escaped
    world and enters raw HTML string construction.

## Sensitive Data Paths

| Data Type | Source | Destination | Protection |
|---|---|---|---|
| Customer record values (row/cell data) | AppSheet table query (`table.queryRowValues`) | Chart series data, axis categories, pie slice names, tooltip HTML | Access-controlled server-side; **unescaped** once inside custom `formatter` callbacks |
| Column display names / chart titles | App creator's saved view definition (`ChartConfig`) | Axis names, series names, `title.text`, tooltip label prefixes | Creator-authored; treated as trusted markup by the library |
| Customer app names and creator email addresses (PII) | AppSheet Admin Console APIs | Admin Console tooltip HTML via the shared `tooltipFormatter` | Interpolated into an HTML string with no escaping |
| Customer-supplied app logo URLs | App metadata | `rich[...].backgroundColor.image` on axis labels | Loaded as an image resource from the AppSheet origin |
| Chart bitmap / SVG export | Rendered canvas or SVG root | `toDataURL`, download anchor, or a new browser tab | Contains whatever customer data is on-screen; written via `document.write` in the fallback path |

## Privileged Actions

| Action | Location | Guard |
|---|---|---|
| HTML injection into the live DOM | `TooltipHTMLContent.setContent` → `el.innerHTML` | Pass-through Trusted Types policy `TooltipHTMLFix2` (`createHTML: s => s`) — **no effective guard** |
| Trusted Types policy creation (per render) | `TooltipHTMLContent.setContent` (`TooltipHTMLFix1/2/3`) | None; requires the policy names to be CSP-allow-listed, and duplicates to be permitted |
| Inline CSS injection | `TooltipHTMLContent.show` → `el.style.cssText` (`extraCssText`) | None |
| Unpoliced HTML injection | `TooltipHTMLContent.setContent` → `arrowEl.innerHTML` (DOM-content branch) | None |
| Dynamic code evaluation | `GeoJSONResource.ts:parseInput` → `new Function(...)` | Reachable only when `JSON.parse` is unavailable |
| HTML injection (toolbox) | `DataView.ts` → `header.innerHTML`, `viewMain.innerHTML`, `closeButton.innerHTML`, `refreshButton.innerHTML` | None; feature is opt-in via `toolbox.feature.dataView` |
| New-window document write | `SaveAsImage.ts` → `tab.document.write(html)`, `doc.write(bstr)` | None; markup built by string concatenation |
| SVG DOM replacement | `echarts.ts` → `(zr.painter as SVGPainter).getSvgRoot().innerHTML = content` | None; connected-charts export path |
| Outbound network request | `graphic` `type: 'image'` / `rich[...].backgroundColor.image` | None; arbitrary URL fetched from the AppSheet origin |
| Shipping pre-built browser bundles | `dist/echarts*.js`, `dist/echarts*.min.js` | Committed artifacts; not verifiably reproducible from `src/` (see below) |

**Fork-patch coverage across committed bundles** — the patches applied to `src/`
are not uniformly present in `dist/`:

| Bundle | `TooltipHTMLFix1` | `TooltipHTMLFix2` | `TooltipHTMLFix3` | State |
|---|---|---|---|---|
| `echarts.js` / `echarts.min.js` | yes | yes | yes | Matches `src/` (HEAD) |
| `echarts.common.js` / `.common.min.js` | yes | yes | yes | Matches `src/` (HEAD) |
| `echarts.esm.js` / `.esm.min.js` | yes (×2) | **no** | **no** | Stale at commit `4e53257` |
| `echarts.simple.js` / `.simple.min.js` | **no** | **no** | **no** | Unpatched upstream code |

`package.json` sets `main: dist/echarts.js` (patched) and `module: index.js`
(compiled from patched `src/`), so the default resolution paths are current.
AppSheet imports the library as `import('echarts')` (full bundle, not
tree-shaken), which resolves to `main`/`module`. The `esm` and `simple` bundles
remain divergent and should be regenerated or removed.

## Consumer Context (AppSheet)

Recorded here because it determines exploitability of the sinks above.

-   **Dependency pin:** `Nirvana/Content/package.json` declares
    `"echarts": "git+https://appsheet-third-party.googlesource.com/echarts"` with
    **no `#ref` and no semver constraint** — it tracks the fork's default
    branch. `package-lock.json` resolves it to
    `#967afa1ae54628568880206a569b42d40189f566` with **no `integrity` hash**
    (npm omits subresource integrity for git dependencies). A push to the fork's
    `main` therefore lands in AppSheet on the next lockfile refresh, with no
    hash pinning.
-   **Primary consumer:** `Nirvana/Content/components/app/primary/ChartView.tsx`
    renders end-user-facing chart views. Chart configuration is read from the
    app creator's saved view definition (`ChartConfig`); row data is pulled via
    `table.queryRowValues` and passed into the option builders under
    `src/editor/charts/helpers/create_chart_option/`.
-   **Function formatters returning HTML built from record data:**
    `ChartView.tsx` (scatter tooltip, joins `value[i]` with `<br/>`),
    `bar_chart_builder.ts` (`getBarLineAreaTooltips`), and
    `scatter_chart_builder.ts` all concatenate row values and creator-authored
    column display names into HTML strings with no escaping.
-   **Admin Console:** `components/admin/console/overview/echarts_options.ts`
    exports a shared `tooltipFormatter` that interpolates `data.name` and
    `data.value` into a `<p>`/`<span>`/`<b>` HTML string. Its callers pass
    customer-authored app names (`PopularAppsCard.tsx`) and creator email
    addresses (`MostAppsOwnedCard.tsx`).
-   **Rich-text templates fed by data:** `pie_chart_builder.ts` and
    `kpi_helper_functions.ts` build `{bold|...}` / `{header|...}` rich-text
    tokens from row values and series names.
-   **Configuration not used:** No `renderMode`, `appendToBody`, `appendTo`, or
    `graphic` configuration appears anywhere in the AppSheet frontend, so
    tooltips use the default `renderMode: 'html'` — i.e. the `innerHTML` path
    above — and the tooltip DOM stays within the chart container.
-   **No sanitization wrapper:** No DOMPurify or equivalent escaping is applied
    to any ECharts formatter output in the AppSheet frontend.

## Priority Review Areas

1.  **Pass-through Trusted Types policy in `TooltipHTMLContent.setContent`** —
    the fork's `createHTML: (string) => string` identity policy launders
    arbitrary strings into `TrustedHTML`, silencing the violation while removing
    the protection; this is the single highest-value finding in the repository
    and should be replaced with real sanitization.
2.  **Function-`formatter` → `innerHTML` DOM-XSS chain** — AppSheet's tooltip
    formatters concatenate end-user record values and creator-authored column
    names into HTML with no escaping, and the library performs none on the
    callback return path, giving a direct customer-data-to-script-execution
    route in the AppSheet origin.
3.  **`extraCssText` raw CSS injection** — `tooltipModel.get('extraCssText')` is
    concatenated straight into `el.style.cssText`, permitting arbitrary
    declarations and CSS-based data exfiltration if it is ever fed
    configuration-derived text.
4.  **Unpatched HTML sinks outside the tooltip** — `DataView.ts`,
    `SaveAsImage.ts`, the connected-charts SVG export in `echarts.ts`, and the
    `arrowEl.innerHTML` branch received no fork hardening and will either bypass
    or break under Trusted Types enforcement.
5.  **`new Function` evaluation in `GeoJSONResource.parseInput`** — a dynamic
    code-execution primitive reachable from `registerMap` input whenever
    `JSON.parse` is unavailable; confirm unreachability or remove the fallback.
6.  **`dist/` bundle divergence and unpinned dependency resolution** — the
    committed `esm` and `simple` bundles do not correspond to `src/`, the
    bundles are unverifiable build artifacts shipped to browsers, and AppSheet
    consumes the fork from a branch reference with no integrity hash, so this is
    a supply-chain integrity gap in addition to a patch-coverage gap.
7.  **Stale upstream baseline** — pinned to ECharts `5.4.0` (November 2022) and
    a `zrender` nightly pre-release, with no rebase since; any upstream ECharts
    or zrender security fix released after that date is presumed missing.
8.  **Rich-text token injection in canvas labels** — unescaped `{`, `}`, and `|`
    in row values can break out of `{style|text}` templates in the pie and KPI
    label formatters, causing label spoofing and rendering-integrity issues
    (not XSS, as these are canvas-rendered).

## Out of Scope

Teams can fill out this section with any known filed vulnerability bugs that
they've determined should be out of scope from future Fortify bug filing.
