CVE-2026-71321 Overview
CVE-2026-71321 is an unauthenticated denial of service vulnerability in Nuxt, an open-source web development framework for Vue.js. The flaw affects the internal island renderer endpoint /__nuxt_island/... in versions from 3.1.0 up to but not including 3.21.10 and 4.5.1. The endpoint decodes and hashes attacker-controlled JSON body input with destr and ohash before validating the URL-resident hash. An unauthenticated POST /__nuxt_island/_.json request with a large JSON body is fully read, parsed, and hashed prior to rejection. The wasted CPU cycles on the Nitro single event loop delay concurrent requests, degrading service availability. The issue is categorized under [CWE-407] (Inefficient Algorithmic Complexity).
Critical Impact
Unauthenticated attackers can send oversized JSON payloads to the island renderer endpoint to exhaust CPU on the Nitro single event loop and stall concurrent request processing.
Affected Products
- Nuxt versions 3.1.0 through 3.21.9
- Nuxt versions 4.0.0 through 4.5.0
- Applications exposing the internal /__nuxt_island/ renderer endpoint
Discovery Timeline
- 2026-08-05 - CVE-2026-71321 published to NVD
- 2026-08-05 - Last updated in NVD database
- Fixed releases: Nuxt v3.21.10 and Nuxt v4.5.1
Technical Details for CVE-2026-71321
Vulnerability Analysis
The Nuxt island renderer endpoint processes server-side component rendering requests through a URL-embedded hash validation scheme. The endpoint expects the client to submit props in the JSON body along with a matching hash in the URL path. However, the implementation performs the expensive work of body parsing and hashing before comparing the computed hash against the URL-resident hash. An attacker submits an arbitrarily large JSON body to POST /__nuxt_island/_.json without any valid hash. The server reads the entire body, calls destr for JSON parsing, and then computes an ohash of the parsed structure. All of this work occurs on the Nitro single event loop before the hash mismatch causes rejection. Because Node.js runs a single event loop per process, this CPU-bound work blocks concurrent request handling, resulting in a denial of service condition with no authentication and no valid hash required.
Root Cause
The root cause is validation-after-work ordering in the island props handler. The endpoint places the expensive decode and hash operations before the authorization check represented by the hash comparison. Because the input size and JSON nesting depth were unbounded, an attacker controlled both the parsing cost and the hashing cost of every unauthenticated request.
Attack Vector
Exploitation requires only network access to any endpoint reachable at /__nuxt_island/*.json. No credentials, session, or valid hash are needed. A remote attacker sends POST requests with large or deeply nested JSON payloads. Each request consumes CPU on the Nitro event loop, stalling legitimate concurrent requests and degrading application availability.
// Security patch: packages/nitro-server/src/runtime/utils/island-props.ts
// fix(nitro): bound island props and v-for to prevent unauthenticated DoS
// Guards applied to the raw island request body before it is parsed and hashed, so an
// oversized or deeply nested payload is rejected before that work runs on unauthenticated
// input.
/** @internal */
export const MAX_ISLAND_BODY_BYTES = 64 * 1024
/** @internal */
export const MAX_ISLAND_PROP_DEPTH = 64
/**
* Whether the bracket nesting of a JSON-ish string exceeds `maxDepth`, in a single linear
* pass. Brackets inside string values are ignored.
*
* @internal
*/
export function exceedsMaxDepth (raw: string, maxDepth = MAX_ISLAND_PROP_DEPTH): boolean {
let depth = 0
let inString = false
let escaped = false
for (let i = 0; i < raw.length; i++) {
const ch = raw[i]
if (inString) {
if (escaped) {
escaped = false
} else if (ch === '\\') {
escaped = true
} else if (ch === '"') {
inString = false
}
}
// ...
}
}
Source: GitHub Commit 4e35ae9. The patch introduces MAX_ISLAND_BODY_BYTES (64 KB) and MAX_ISLAND_PROP_DEPTH (64) constants applied to the raw body before destr parsing and ohash hashing occur.
Detection Methods for CVE-2026-71321
Indicators of Compromise
- Repeated POST requests to URLs matching the pattern /__nuxt_island/*.json from unauthenticated sources.
- Request bodies exceeding 64 KB targeting the island renderer endpoint.
- Sustained high CPU utilization on Node.js Nitro server processes correlated with island endpoint traffic.
- Elevated latency on unrelated application endpoints served by the same Nuxt instance.
Detection Strategies
- Log and inspect HTTP request bodies routed to /__nuxt_island/ for oversized or deeply nested JSON structures.
- Alert on rate anomalies for POST requests to island endpoints from single source IPs.
- Correlate spikes in Node.js event loop lag metrics with island endpoint request patterns.
Monitoring Recommendations
- Track event_loop_lag and CPU utilization metrics on Nitro server processes and alert on sustained thresholds.
- Enable web server access logging with request size fields for all /__nuxt_island/ paths.
- Deploy a web application firewall (WAF) rule to log payloads over 64 KB posted to island endpoints.
How to Mitigate CVE-2026-71321
Immediate Actions Required
- Upgrade Nuxt to version 3.21.10 or 4.5.1 immediately in all affected deployments.
- Restrict external access to /__nuxt_island/ paths at the reverse proxy or WAF layer if immediate upgrade is not possible.
- Enforce a request body size limit of 64 KB or lower on the island renderer endpoint at the ingress layer.
Patch Information
Nuxt released fixes in v3.21.10 and v4.5.1. The patches, applied in commits 4e35ae9 and 668cdfd, bound the raw island request body to 64 KB and cap JSON bracket nesting at depth 64 before any destr parsing or ohash hashing runs. See the GitHub Security Advisory GHSA-9pgf-384g-p7mv for full details.
Workarounds
- Block or rate-limit unauthenticated POST requests to /__nuxt_island/*.json at the reverse proxy.
- Configure ingress-level request body size limits to reject payloads larger than 64 KB targeting island paths.
- Deploy WAF rules that reject deeply nested JSON structures on the island renderer endpoint.
# Example nginx configuration to bound island endpoint request size
location ~ ^/__nuxt_island/ {
client_max_body_size 64k;
limit_req zone=island_zone burst=5 nodelay;
proxy_pass http://nuxt_upstream;
}
# Define rate limit zone in http context
# limit_req_zone $binary_remote_addr zone=island_zone:10m rate=10r/s;
Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.

