Overview
A critical cross-site scripting (XSS) vulnerability has been disclosed in justhtml, a popular Python HTML sanitization and parsing library. Tracked as CVE-2026-7808, the flaw affects all versions prior to 1.16.0 and exposes multiple code paths through which dangerous content — including <script> and <style> tags — can bypass the library's sanitization layer entirely.
The vulnerability is particularly concerning for applications relying on justhtml to render user-supplied HTML safely. Despite appearing sanitized, crafted input can survive the pipeline and reach downstream users, enabling stored or reflected XSS.
Technical Details
| Field | Value |
|---|---|
| CVE ID | CVE-2026-7808 |
| CVSS 3.1 | 9.8 (Critical) |
| CVSS 4.0 | 9.3 (Critical) |
| Attack Vector | Network |
| Authentication | None Required |
| Privileges Required | None |
| User Interaction | None |
| Fixed In | justhtml 1.16.0 |
| GitHub Advisory | GHSA-4p64-v8f5-r2gx |
| Disclosed | 2026-08-23 |
Bypass Mechanisms
The advisory identifies several distinct sanitization bypass paths:
1. Mixed-Case Tag Names
The sanitize() and sanitize_dom() functions perform case-sensitive tag matching in certain code paths. Attackers can smuggle tags like <ScRiPt> or <StYlE> through programmatic DOM input, where they are not normalized before the allowlist check.
2. Mutable Policy Objects Sanitization policy objects — including the exported defaults — can be mutated or reused across sanitization calls. Doing so weakens subsequent sanitizations as internal state from prior calls bleeds into the next invocation, creating windows where the effective policy diverges from the configured one.
3. Crafted Doctype Names Specially crafted doctype names can be serialized back into active markup during round-trip parsing, reintroducing content that was ostensibly stripped.
4. SVG/MathML Animation and URL References
Custom policies that preserve SVG or MathML namespaces can inadvertently permit animation elements or url(...) references in CSS presentation attributes, allowing foreign-content bypass of the main sanitization checks.
Impact Assessment
Who Is at Risk
Applications relying on justhtml to sanitize user-supplied HTML before rendering are affected. The risk is highest in scenarios involving:
- Comment systems, rich-text editors, or user profile fields rendering HTML
- Document viewers or email previewers that pipe external content through justhtml
- Server-side rendered pages where sanitized HTML is emitted directly into the DOM
- Applications using custom or cloned policy objects rather than fresh policy instances per call
Potential Attack Chains
- Stored XSS — Attacker submits crafted HTML (e.g., mixed-case
<ScRiPt>) through a form; it is stored and later rendered to other users, executing arbitrary JavaScript in victim sessions - Session Hijacking — XSS payload exfiltrates session cookies or authentication tokens
- Credential Phishing — Injected UI elements overlay legitimate page content to collect credentials
- CSRF Chain — Injected scripts make authenticated requests on behalf of the victim
Mitigation
Immediate Action: Upgrade to justhtml 1.16.0
The only complete fix is upgrading to justhtml >= 1.16.0, which addresses all known bypass paths identified in CVE-2026-7808.
pip install --upgrade justhtml
# Verify
python -c "import justhtml; print(justhtml.__version__)"Interim Hardening
If upgrading immediately is not possible:
- Use fresh policy instances per sanitization call — never reuse or mutate policy objects
- Avoid advanced programmatic DOM input — limit use to the standard
JustHTML(input, sanitize=True)API which is less affected - Disable SVG/MathML preservation in custom policies unless strictly required
- Normalize tag case before passing to justhtml — a pre-pass lowercasing all tags reduces the mixed-case attack surface
- Implement a Content Security Policy (CSP) with strict
script-srcas a defence-in-depth layer — CSP will not prevent injection but will limit execution
Verification
After upgrading, verify the bypass is patched:
from justhtml import JustHTML
# These should now be stripped
result = JustHTML('<ScRiPt>alert(1)</ScRiPt>', sanitize=True)
assert '<script' not in str(result).lower(), "Sanitization bypass still present!"
print("Sanitization working correctly.")Detection Opportunities
Review application logs and sanitized output for indicators of attempted exploitation:
- HTML stored in databases containing mixed-case tag names (
ScRiPt,ImG,OnErRoR) - Unexpected
<script>,<style>, or<iframe>tags surviving sanitization in rendered output - User submissions containing
javascript:,data:text/html, or SVG animation attribute strings - Error logs from downstream HTML parsers encountering unexpected tag types
Background: justhtml
justhtml is a Python library for parsing and sanitizing HTML, with a primary use case of safely rendering user-supplied content. It is used in web applications, content management systems, and email processing pipelines. The library's popularity makes CVE-2026-7808 a high-priority fix across the Python web ecosystem — any application processing untrusted HTML should treat this as an urgent upgrade.