Skip to main content
Vulnerability Database/CVE-2026-94484

CVE-2026-94484: Vercel Next.js Cache Poisoning DOS Vulnerability

CVE-2026-94484 is a cache poisoning denial of service vulnerability in Vercel Next.js that allows attackers to cause persistent DOS through crafted requests. This post explains its impact, affected versions, and mitigation steps.

Published:

CVE-2026-94484 Overview

CVE-2026-94484 is a cache poisoning vulnerability in Vercel Next.js, a React framework for building full-stack web applications. The flaw affects versions 15.0.0 through 15.5.26 and the 16.x branch prior to 16.3.8. Applications that define a root-level catch-all page alongside statically generated or Incremental Static Regeneration (ISR) routes can share a response cache key that is insufficiently scoped to its source route. A single unauthenticated crafted request can poison the cache, substituting content across users or causing persistent denial of service until the entry revalidates. The issue is tracked as [CWE-524: Use of Cache Containing Sensitive Information].

Critical Impact

One unauthenticated HTTP request can poison a shared cache entry, forcing cross-user content substitution or persistent denial of service on affected Next.js routes.

Affected Products

  • Vercel Next.js versions 15.0.0 through 15.5.26
  • Vercel Next.js versions 16.0.0 through 16.3.7
  • Next.js applications using a root-level catch-all page with SSG or ISR routes

Discovery Timeline

  • 2026-10-02 - CVE-2026-94484 published to the National Vulnerability Database (NVD)
  • 2026-10-05 - Last updated in NVD database

Technical Details for CVE-2026-94484

Vulnerability Analysis

The vulnerability resides in how Next.js computes response cache keys for statically generated and Incremental Static Regeneration routes. When an application defines a root-level catch-all page (for example, app/[...slug]/page.tsx), the response cache can reuse a key that does not uniquely identify the source route. Multiple logical routes resolve to the same cache slot, allowing an attacker's response to be served to subsequent visitors of a different route.

The practical impact splits into two outcomes. Attackers can substitute content across users on cached pages, which breaks tenant or page isolation. Alternatively, they can insert a malformed or error response into the cache, producing persistent denial of service until the stale entry revalidates or is evicted.

Exploitation requires no authentication and no user interaction, but the attack complexity is elevated because the attacker must shape a request that aligns with the ambiguous cache key for a target route.

Root Cause

The underlying defect is a scoping error in cache key generation. The response cache key did not include a stable identifier of the source route, so distinct routes could collide on the same key. The fix introduces a dedicated route-cache-key helper and an isRouteCacheOwner check that confirms a cache entry belongs to the route that is attempting to read or write it.

Attack Vector

The attack vector is network-based. An unauthenticated remote attacker sends a crafted HTTP request to a Next.js deployment that uses a root-level catch-all page together with SSG or ISR. The response is written into a shared cache entry. Subsequent requests from other users for an affected route receive the attacker-influenced response until the entry is revalidated or replaced.

typescript
// Patch excerpt: packages/next/src/build/index.ts
// Scope response cache keys to their source route (#219)
+import {
+  getRouteCacheKey,
+  ROUTE_CACHE_DIRECTORY,
+} from '../server/lib/route-cache-key'
+import { RouteKind } from '../server/route-kind'
 import type { AppBuildManifest } from './webpack/plugins/app-build-manifest-plugin'
 import type { PagesManifest } from './webpack/plugins/pages-manifest-plugin'
typescript
// Patch excerpt: packages/next/src/build/templates/app-page-runtime.ts
// Adds route ownership validation at request time
+import { isRouteCacheOwner } from '../../server/lib/route-cache-key'
   with { 'turbopack-transition': 'next-server-utility' }

Source: Next.js Commit 52c94ab and Next.js Commit 719e4c.

Detection Methods for CVE-2026-94484

Indicators of Compromise

  • Cached HTML responses whose body does not match the requested route path or expected template.
  • Unexpected HTTP 4xx or 5xx responses served from cache for routes known to be healthy at origin.
  • Spikes in x-nextjs-cache: HIT responses for routes immediately after a single anomalous upstream miss.
  • User reports of seeing content intended for a different page or tenant on catch-all routes.

Detection Strategies

  • Inventory Next.js deployments and flag versions in the ranges 15.0.0 to 15.5.26 and 16.0.0 to 16.3.7 that use a root-level catch-all route with SSG or ISR.
  • Compare rendered response fingerprints against expected route templates in staging to detect cross-route substitution.
  • Review web application firewall and CDN logs for crafted requests to catch-all paths followed by cache HITs on unrelated routes.

Monitoring Recommendations

  • Enable verbose logging on the Next.js response cache layer and alert on key collisions.
  • Monitor origin error rates versus edge-cached error rates to detect poisoned error responses persisting at the edge.
  • Track revalidation events and purge activity for ISR routes to confirm poisoned entries are evicted after patching.

How to Mitigate CVE-2026-94484

Immediate Actions Required

  • Upgrade Next.js to version 15.5.27 on the 15.x branch or 16.3.8 on the 16.x branch.
  • Purge the full response cache and ISR cache after upgrading to remove any already-poisoned entries.
  • Audit application routing for root-level catch-all pages combined with SSG or ISR and document their exposure.

Patch Information

Vercel fixed the issue by scoping response cache keys to their source route and adding ownership validation on cache reads. The fixes are available in Next.js Release v15.5.27 and Next.js Release v16.3.8. Full details are published in GitHub Security Advisory GHSA-mcj8-r9mp-w47p.

Workarounds

  • Remove or restructure root-level catch-all pages (app/[...slug]/page.tsx) until the upgrade is applied.
  • Disable Incremental Static Regeneration on routes that share key space with a catch-all route.
  • Place a CDN or reverse proxy cache rule in front of Next.js that keys responses by the full normalized path to reduce collisions.
bash
# Upgrade Next.js to a patched release
npm install next@15.5.27
# or for the 16.x branch
npm install next@16.3.8

# Purge the on-disk Next.js build and cache after upgrading
rm -rf .next/cache
npm run build

Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.

Experience the Most Advanced Cybersecurity Platform

See how the world’s most intelligent, autonomous cybersecurity platform can protect your organization today and into the future.