CVE-2026-90561
Executive Summary
CVE-2026-90561 is a stored cross-site scripting (XSS) vulnerability in the Strapi headless CMS content manager WYSIWYG preview component, which fails to strip <script> tags from rich text fields. Strapi deployments running 4.x through 4.26.2 and 5.x before 5.48.1 are affected. A low-privileged Author-role user can persist malicious script content that executes in the session of a higher-privileged user (Editor or Super Admin) when the preview pane is expanded, enabling full account takeover of the privileged session.
This record — and 170,000+ others — are available via the ValtersIT API. One endpoint replaces five: NVD + GitHub CVE + CISA KEV + EPSS + Nuclei + Exploit-DB, unified.
No signup required
Technical Analysis
The vulnerability resides in the content manager's WYSIWYG preview rendering path. Strapi stores rich text content authored by users and renders a preview of that content inside the administrative content manager UI. Per the NVD description, the preview component "fails to strip script tags from rich text." This is a classic stored (persistent) XSS condition, classified CWE-79.
The root cause is insufficient/absent server-side and client-side sanitization of rich text input before it is rendered into the DOM. Because the preview pane renders stored content without neutralizing <script> elements, injected script executes with the origin and privileges of the Strapi administration interface in the browser session of whichever user views the preview.
Two properties make this notably severe:
- Privilege asymmetry. The attacker needs only the low-privileged Author role, which is normally permitted to create and edit content. The victim is an Editor or Super Admin — roles with far greater authority (publishing, user management, configuration, API token issuance).
- Session-context execution. Script executed in the admin origin inherits the authenticated session context and same-origin access to admin APIs. Under the CVSS scope-changed (
S:C) rating, the compromised component (content authoring) enables impact to resources beyond that component (the administrative session and the accounts it controls).
CVSS 8.7 reflects: network attack vector (AV:N), low attack complexity (AC:L), low privileges required (PR:L — Author role), user interaction required (UI:R — victim must expand the preview pane), scope change (S:C), high confidentiality (C:H) and high integrity (I:H) impact, and no availability impact (A:N).
Notably, no patch evidence has been identified from tracked sources: patch confidence is 0/4, and no affected-version package data was published via OSV in this dataset. Treat all versions in the stated ranges as vulnerable until a vendor fix is confirmed and validated.
Exploitation Scenarios
No public PoC, exploit code, or Nuclei template is available for this CVE. The attack chain below is inferred strictly from the NVD description and the stored-XSS vulnerability class; no function names, endpoints, or parameters beyond those in the description are asserted.
Reconnaissance / target identification. The attacker identifies a Strapi instance in the affected version range (4.x ≤ 4.26.2, or 5.x < 5.48.1). Strapi admin interfaces are commonly exposed on port 1337 or behind a reverse proxy at
/admin. The attacker needs valid credentials for a low-privileged Author account — obtainable via credential stuffing, phishing, leaked credentials, or a legitimate low-trust account (e.g., a contractor or content contributor).Trigger the flaw class. Authenticated as an Author, the attacker creates or edits a content entry containing a rich text field. Into that field they store content that includes
<script>tags. Because the vulnerable preview component does not strip script tags from rich text, the malicious markup is persisted in the CMS database.Payload / execution. When a higher-privileged user (Editor or Super Admin) opens the content entry and expands the preview pane, the stored rich text is rendered by the vulnerable preview component. The browser parses the injected script as executable content in the context of the Strapi admin origin — this is the stored XSS trigger, requiring the victim's interaction of expanding the preview.
Post-exploitation impact. Script executing in the admin origin can act with the victim's session, supporting account takeover of the privileged user. Representative outcomes consistent with
C:H/I:Hinclude theft of the victim's authenticated session context and abuse of the admin APIs available to the Editor/Super Admin role (content manipulation, configuration changes, or creation of API tokens/users, depending on role permissions). Because the injected payload persists in stored content, it can trigger against any privileged user who previews the entry — a one-to-many victim model.
Impact Assessment
Business impact is high. A single compromised Author account can be leveraged to harvest privileged administrative sessions, effectively escalating from content author to Super Admin — the highest trust level in the CMS. Strapi frequently acts as the backend content API for web and mobile applications, so administrative compromise can cascade to published content integrity, downstream application behavior, and any systems trusting Strapi-issued API tokens.
Blast radius considerations:
- Confidentiality (High): Attacker script runs in the admin origin and can access data the privileged session can reach.
- Integrity (High): Content, configuration, and user/role data reachable by the victim's role are manipulable.
- Scope Changed: Impact crosses from the authoring component to the broader admin session/accounts.
- Availability (None): The vulnerability class does not inherently disrupt service.
Detection is complicated because the payload is stored, benign-looking at the database layer, and triggers on a legitimate user action (opening a preview) rather than an anomalous network request. CISA KEV status is NO, and no in-the-wild exploitation is confirmed in this dataset — but the low privilege requirement, scope change, and one-to-many persistence make this attractive for targeted attacks against content-driven organizations.
Detection Guidance
Sigma Rule
title: Strapi WYSIWYG Preview Stored XSS Payload Stored in Rich Text
id: 3f9a1c72-5b64-4e21-9c0d-90561strapi
status: experimental
description: Detects creation or update of rich text content containing script tags, consistent with CVE-2026-90561 stored XSS in the Strapi content manager preview component.
references:
- https://nvd.nist.gov/vuln/detail/CVE-2026-90561
author: valtersit.com
date: 2026-01-01
logsource:
category: application
product: strapi
detection:
selection_event:
event.action|contains:
- 'update'
- 'create'
selection_payload:
request.body|contains:
- '<script'
- '</script'
- '<script>'
- 'javascript:'
condition: selection_event and selection_payload
falsepositives:
- Legitimate authors discussing HTML/scripting in documentation content (sanctioned use)
level: high
tags:
- attack.t1189
- cwe.79
YARA Rule
rule CVE_2026_90561_Strapi_RichText_ScriptInjection
{
meta:
description = "Detects script tags embedded in Strapi rich text content associated with CVE-2026-90561 stored XSS"
author = "valtersit.com"
reference = "https://nvd.nist.gov/vuln/detail/CVE-2026-90561"
date = "2026-01-01"
severity = "high"
strings:
$s1 = "<script" ascii nocase
$s2 = "</script>" ascii nocase
$s3 = "javascript:" ascii nocase
$s4 = "onerror=" ascii nocase
$s5 = "onload=" ascii nocase
condition:
any of ($s*)
}
Suricata IDS Rule
alert http any any -> any any (msg:"CVE-2026-90561 Strapi Rich Text Stored XSS Script Tag Injection"; flow:established,to_server; http.method; content:"POST"; http.request_body; content:"<script"; nocase; http.request_body; content:"</script"; nocase; classtype:web-application-attack; reference:cve,2026-90561; sid:9005611; rev:1;)
Elastic Detection
sequence by user.name with maxspan=1m
[any where event.category == "web" and http.request.method == "POST" and
stringContains(http.request.body, "<script")]
[any where event.category == "authentication" and event.action == "user_session_change"]
Splunk SPL Query
index=web sourcetype=strapi_access
| search (uri_path="*/content-manager/*" OR uri_path="*/api/*")
| eval body=coalesce(request_body, body, form_data)
| where match(body, "(?i)<\s*script") OR match(body, "(?i)</\s*script") OR match(body, "(?i)javascript:")
| stats count min(_time) as first_seen max(_time) as last_seen by src_ip, user, uri_path
| sort - count
| convert ctime(first_seen) ctime(last_seen)
Wazuh OSSEC Rule
<group name="web,appsec,strapi,">
<rule id="905610" level="12">
<decoded_as>json</decoded_as>
<field name="http.method">POST</field>
<regex field="http.request.body" type="pcre2">(?i)<\s*script</regex>
<description>CVE-2026-90561: Possible Strapi stored XSS - script tag in rich text submission</description>
<mitre>
<id>T1189</id>
</mitre>
<group>cve_2026_90561,</group>
</rule>
</group>
Mitigation & Patch Guidance
Patch confidence: 0/4 (UNPATCHED — no patch evidence from any tracked source). No vendor fix, workaround, or OSV package record was provided in this dataset. Until a vendor-confirmed release is verified, apply compensating controls.
Immediate mitigations
- Restrict the Author role: limit who can create/edit rich text content, and review accounts holding the Author role for legitimacy.
- Apply a Web Application Firewall / reverse-proxy rule that inspects submissions to content-manager endpoints for
<scriptand event-handler attributes; block or strip on match (see rules above). - Add output sanitization at the preview layer where possible (e.g., consume rich text as sanitized HTML rather than raw DOM injection) — validate against your Strapi version before relying on it.
- Enable strict Content-Security-Policy for the admin interface to reduce the impact of inline script execution.
- Monitor privileged accounts for anomalous admin-API activity following any preview of untrusted content.
Patch / upgrade steps
- No patch evidence exists in tracked sources. Monitor the official Strapi repository/advisories for a fixed release addressing CVE-2026-90561.
- The NVD description cites affected ranges 4.x ≤ 4.26.2 and 5.x < 5.48.1, implying a fix is expected around 4.26.3 (4.x) and 5.48.1 (5.x). Verify these versions exist and remediate the CVE before deploying — do not treat them as confirmed patches.
- Until validated, upgrade to the latest available release and re-test the preview behavior with a controlled
<script>payload in a staging environment.
Long-term hardening
- Enforce context-aware output encoding and server-side HTML sanitization (allowlist-based) for all rich text rendering paths.
- Adopt least privilege for content roles; separate authoring from publishing.
- Deploy CSP and secure session cookies for the admin origin; shorten admin session lifetimes.
- Integrate SAST/DAST for stored-XSS patterns into the CI/CD pipeline for CMS plugins and content components.
- Continuously track vendor advisories and OSV for this CVE; re-evaluate patch confidence as data becomes available.
References
- NVD — CVE-2026-90561: https://nvd.nist.gov/vuln/detail/CVE-2026-90561
- MITRE CWE-79 (Improper Neutralization of Input During Web Page Generation — Cross-site Scripting): https://cwe.mitre.org/data/definitions/79.html
- MITRE ATT&CK T1189 (Drive-by Compromise): https://attack.mitre.org/techniques/T1189/
- Strapi official security advisories / releases (monitor for CVE-2026-90561 fix): https://github.com/strapi/strapi/security/advisories
- OWASP Cross Site Scripting Prevention Cheat Sheet: https://cheatsheetseries.owasp.org/cheatsheets/Cross_Site_Scripting_Prevention_Cheat_Sheet.html
Exploit-in-the-wild note: CISA KEV status is NO; no public PoC, exploit code, or Nuclei template was identified in this dataset. No threat actor campaign is confirmed. All exploitation detail above is inferred from the NVD description and the stored-XSS vulnerability class.
What is this? Security researchers use these exact search queries on Shodan.io (a search engine for internet-connected devices) to find vulnerable systems globally. You can copy these dorks to see if your organization's IP space is exposed.
💣 PoC CODE AVAILABLE
Exploit code for this CVE is tracked in our database.
Access poc_code via API Pro.