T09 · Insecure Skill Coding Practices
- Location
scripts/build-report.mjs:65- Finding
Stored Script Injection Through Unsafe Report Payload Embedding
- Content
View full analysis
// Default is a PLACEHOLDER sentinel, never a plausible-looking example. If injection // fails for any reason, the page must shout "not built" instead of rendering a fake // report — that exact silent-default failure shipped a blank report once. const DATA = /*SLOP_DATA*/{ "__notBuilt__": true }/*END_SLOP_DATA*/; ``` ### Technical Analysis The report builder uses `JSON.stringify()` and inserts the resulting text directly into an inline `` sequence. The HTML parser recognizes `` even when it appears inside a JavaScript string literal. Therefore, a payload field containing content such as: ```html ``` can terminate the legitimate report script and create a new executable script element. This condition is reachable because the report schema includes repository-derived values such as project names, file paths, finding descriptions, and fix-it prompts. A malicious repository can influence these valu ...[truncated 2292 chars]- Remediation
View remediation
/g, '\\u003e') .replace(/\u2028/g, '\\u2028') .replace(/\u2029/g, '\\u2029'); const out = template.replace( ANCHOR, '$1/*SLOP_DATA*/' + serializedPayload + '/*END_SLOP_DATA*/' ); ``` Escaping `<` prevents an attacker from creating the `` delimiter. 2. **Prefer a non-executable JSON container.** Place the serialized payload in an element such as: ```html ``` Then parse it using: ```js const DATA = JSON.parse(document.getElementById('slop-data').textContent); ``` The payload must still have `<` escaped because the HTML parser recognizes `` regardless of the script element's type. 3. **Add regression tests.** Build reports containing adversarial values such as: ```text ``` Verify that: - The generated file contains no literal attacker-controlled `` sequence inside the data block. - The payload remains valid after browser-side parsing. - No injected script executes when the report is opened. 4. **Apply a restrictive Content Security Policy.** Remove inline event handlers and inline executable scripts where practical, then use a policy that disallows unauthorized script execution. A CSP provides defense in depth but should not replace correct serialization. 5. **Treat all repository-derived report fields as untrusted.** Validate types and reasonable size limits for project names, paths, descriptions, category fields, and prompts. Continue using text-safe DOM APIs such as `textContent` wherever HTML markup is unnecessary. ]]>
