T09 · Insecure Skill Coding Practices
Error
- Location
- assets/template.html:6
- Finding
- Unescaped Template Substitution Enables HTML and JavaScript Injection<![CDATA[ ## Vulnerability Details **File Location**: `assets/template.html`, lines 6-34 **Vulnerability Type**: HTML and JavaScript injection through unsafe template interpolation **Risk Level**: High ### Vulnerable Code ```html <title>{{TITLE}}</title> ``` ```html <div class="chart-title">{{TITLE}}</div> ``` ```html <script> var userOption = {{OPTION}}; ``` ### Technical Analysis The template directly interpolates `{{TITLE}}` into HTML title and body contexts and inserts `{{OPTION}}` into an executable JavaScript context. No context-aware escaping, validation, or safe serialization is required by the template or its accompanying instructions. An attacker-controlled title can terminate the surrounding HTML element and introduce arbitrary markup or executable script. For example, a title containing `</title><script>/* attacker code */</script><title>` breaks out of the title element and adds a script to the generated page. The `{{OPTION}}` placeholder presents an additional JavaScript injection path. If option content is inserted as raw text rather than generated through a trusted JSON serializer, an attacker can terminate the expected object expression and append arbitrary JavaScript. Values containing `</script>` can also terminate the surrounding script element because HTML parsing recognizes the closing tag even when it appears inside a JavaScript string. The generated artifact is intended to be saved as an HTML file and opened in a browser, making this a persistent client-side injection vulnerability rather than a transient rendering defect. ### Attack Path 1. An attacker supplies crafted chart input through a title, series label, option value, or other content that reaches `{{TITLE}}` or `{{OPTION}}`. 2. The chart-generation workflow substitutes the attacker-controlled value directly into `assets/template.html`. 3. The resulting HTML file contains attacker-provided markup or JavaScript outside the intended data context. 4. A user opens the ge ...[truncated 1254 chars]
- Remediation
- <![CDATA[ ## Remediation Suggestions 1. **Do not interpolate titles as raw HTML.** Keep the relevant elements empty and assign their content with `textContent`: ```html <title>Chart</title> <div class="chart-title" id="chart-title"></div> ``` ```js document.title = safeTitle; document.getElementById('chart-title').textContent = safeTitle; ``` 2. **Serialize chart options with a trusted JSON serializer.** Generate `{{OPTION}}` using `JSON.stringify` or an equivalent serializer rather than concatenating user-provided JavaScript source. 3. **Escape script-closing sequences.** When embedding serialized JSON inside a script element, encode at least `<`, `>`, `&`, U+2028, and U+2029. In particular, prevent attacker input from producing a literal `</script>` sequence. A safer design is to place serialized data in a non-executable element: ```html <script id="chart-option" type="application/json">SAFE_SERIALIZED_JSON</script> ``` Then parse it: ```js var userOption = JSON.parse( document.getElementById('chart-option').textContent ); ``` The JSON embedded in this element must still be encoded so user input cannot terminate the script element. 4. **Restrict options to data-only JSON.** Reject functions, executable expressions, event-handler attributes, raw HTML fragments, and unexpected object properties unless a documented feature explicitly requires them. 5. **Apply context-specific encoding.** Use HTML text encoding for HTML contexts, attribute encoding for attributes, URL validation for URLs, and JSON encoding for data consumed by JavaScript. A single generic escaping function is not sufficient for all contexts. 6. **Add a restrictive Content Security Policy where deployment permits it.** Move inline JavaScript into a local static file or protect it with a nonce or hash, and restrict `script-src` and `connect-src` to necessary origins. CSP should be treated as defense in depth rather than the primary fix. 7. **Add security regression tests** covering payloa ...[truncated 303 chars]
