GHSA-xgx4-2wgv-4jhm
## Summary The multiVariableText property panel in `@pdfme/schemas` constructs HTML via string concatenation and assigns it to `innerHTML` using unsanitized i18n label values. An attacker who can control label overrides passed through `options.labels` can inject arbitrary JavaScript that executes in the context of any user who opens the Designer and selects a multiVariableText field with no `{variables}` in its text. ## Details When a user selects a multiVariableText schema field that contains no `{variable}` placeholders, the property panel renders instructional text by concatenating i18n-translated strings directly into `innerHTML`. **Vulnerable sink** — `packages/schemas/src/multiVariableText/propPanel.ts:65-71`: ```typescript // Use safe string concatenation for innerHTML const typingInstructions = i18n('schemas.mvt.typingInstructions'); const sampleField = i18n('schemas.mvt.sampleField'); para.innerHTML = typingInstructions + ` <code style="color:${safeColorValue}; font-weight:bold;">{` + sampleField + '}</code>'; ``` The comment on line 64 claims "safe string concatenation" but the result is assigned to `innerHTML` with no HTML escaping applied to `typingInstructions` or `sampleField`. **i18n lookup has no escaping** — `packages/ui/src/i18n.ts:903`: ```typescript export const i18n = (key: keyof Dict, dict?: Dict) => (dict || getDict(DEFAULT_LANG))[key]; ``` This is a plain dictionary lookup — no HTML encoding or sanitization. **Label override via deep merge** — `packages/ui/src/components/AppContextProvider.tsx:57-63`: ```typescript let dict = getDict(lang); if (options.labels) { dict = deepMerge( dict as unknown as Record<string, unknown>, options.labels as unknown as Record<string, unknown>, ) as typeof dict; } ``` User-supplied `options.labels` values are deep-merged into the i18n dictionary with no content sanitization. The Zod schema validates labels as `z.record(z.string(), z.string())` — enforcing type but not content saf
Properties
- ghsa_id
- GHSA-xgx4-2wgv-4jhm
- severity
- medium
- summary
- PDFME has XSS via Unsanitized i18n Label Injection into innerHTML in multiVariableText propPanel
- cvss_score
- 4.4
- cve_id
- GHSA-xgx4-2wgv-4jhm
- cvss_vector
- CVSS:3.1/AV:N/AC:H/PR:L/UI:R/S:C/C:L/I:L/A:N
- is_ghsa_only
- true
- ghsa_published
- 2026-03-20T20:45:08Z
- source_url
- https://github.com/advisories/GHSA-xgx4-2wgv-4jhm
- ghsa_updated
- 2026-03-20T20:45:09Z
Related Entities (3)
AFFECTS (1)
HAS_WEAKNESS (1)
REPORTED_BY (1)
Explore deeper with Ninja Signal's threat intelligence graph