fix(ui): escapeHtml must escape quote characters too

DOM text-node serialization escapes & < > but NOT " or '. Call sites
that interpolate escapeHtml output inside attribute values (title="...",
data-x="...") were vulnerable to attribute-injection: an attacker-
influenced CSS property value (rule.selector, prop.value from the
inspector) or agent status field landing in one of those attributes
could break out with " onload=alert(1).

Add explicit quote escaping in escapeHtml + keep existing callers
working (no breakage — output is strictly more escaped, not less).

Caught by claude adversarial subagent. The earlier banner-layer fix
was the same class of bug but on a different code path.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
Garry Tan
2026-04-20 11:06:54 +08:00
parent 808ce0de8e
commit 4179390799
+7 -1
View File
@@ -955,7 +955,13 @@ function addEntry(entry) {
function escapeHtml(str) {
const div = document.createElement('div');
div.textContent = str;
return div.innerHTML;
// DOM text-node serialization escapes &, <, > but NOT " or '. Call sites
// that interpolate escapeHtml output inside an attribute value (title="...",
// data-x="...") need those escaped too or an attacker-controlled value can
// break out of the attribute. Add both manually.
return div.innerHTML
.replace(/"/g, '&quot;')
.replace(/'/g, '&#39;');
}
// ─── SSE Connection ─────────────────────────────────────────────