CVE-2026-128077: Nuxt: Incomplete fix for GHSA-9v7c-q64q-vv33: a leading `//` in the request path bypasses `server/middleware` path checks and server route rules on page routes
Summary
Since 4.6.0, Nuxt parses a request path that starts with // as a URL with a host before rendering a page, so //x/admin renders the page at /admin. Nitro's routing, Nitro's route rules and server/middleware see the path as //x/admin, so server-side checks keyed on /admin do not apply. The fix for GHSA-9v7c-q64q-vv33 in 4.6.3 covered dot segments but not this form.
Impact
An unauthenticated attacker can bypass server-side controls that match on the request path of a page route.
A route-scoped server handler is skipped:
ts // nuxt.config.ts export default defineNuxtConfig({ serverHandlers: [{ route: '/admin', middleware: true, handler: '~~/server/admin-guard.ts' }], })
ts // server/admin-guard.ts export default defineEventHandler((event) => { if (!isAuthenticated(event)) { throw createError({ statusCode: 401 }) } })
With this handler, /admin returns 401, but //x/admin and ///x/admin render app/pages/admin.vue along with the data it fetches during server rendering. server/middleware that checks event.path.startsWith('/admin') is skipped in the same way.
Server-side redirect and headers route rules are also skipped, so '/admin/': { redirect: '/login' } does not redirect //x/admin/secret, and per-route security headers such as Content-Security-Policy are not sent.
Browsers send a path such as //x/admin as written, so a plain link is enough to reach the page.
Not affected:
- API handlers in server/api and server/routes, which Nitro does not match for these paths. - appMiddleware route rules and middleware declared with definePageMeta, which are matched against the resolved route. - Nuxt 3.x and 4.0.0 to 4.5.x, which pass the path to the page router unchanged, so these requests 404.
Patches
Fixed in @nuxt/nitro-server@4.6.4, which nuxt@4.6.4 depends on. The renderer now uses the request path exactly as Nitro matched it, so a path starting with // no longer resolves to a different page.
Workarounds
Reject request paths that start with // in a server middleware:
ts // server/middleware/double-slash.ts export default defineEventHandler((event) => { if (event.path.startsWith('//')) { throw createError({ statusCode: 404 }) } })
A reverse proxy or CDN that merges repeated slashes before forwarding the request also removes the mismatch.
Credits
Nuxt thanks @kq5y for reporting this issue.
Other sources
Nuxt is an open-source web development framework for Vue.js. From 4.6.0 until 4.6.4, Nuxt parses a request path beginning with // as a URL host before rendering a page, while Nitro server/middleware and routeRules continue to evaluate the original path. An unauthenticated request such as //x/admin can therefore resolve to the /admin page without route-scoped serverHandlers, server/middleware path checks, redirects, or security headers configured for /admin. API handlers in server/api and server/routes, appMiddleware, page middleware are unaffected. This issue is fixed in version 4.6.4.
— MITRE
Affected Software
Remediation
Recommended actions to resolve this vulnerability, in priority order.
- Upgrade
Upgrade
npm/@nuxt/nitro-serverto a version that resolves this vulnerability.Fixed in 4.6.4 - Upgrade
Upgrade
nuxt/nuxtto a version that resolves this vulnerability.Fixed in 4.6.4 - Compensating control
Reject request paths that start with `//` in server middleware.
Event History
Frequently Asked Questions
Which Nuxt deployments are exposed?
Deployments using Nuxt versions since 4.6.0 are affected when they rely on path-based server-side controls for page routes, such as route-scoped server handlers, server middleware, or route rules matching paths like /admin. The affected component is npm/@nuxt/nitro-server.
What does an attacker need to exploit this issue?
No authentication, privileges, or user interaction are required. An attacker sends a request whose path begins with multiple slashes and a host-like segment, such as //x/admin or ///x/admin, to cause rendering of the /admin page while server-side path checks see a different path.
What security controls can be bypassed?
A route-scoped handler configured for /admin can be skipped, and server middleware that checks whether event.path starts with /admin is skipped in the same way. This can expose the page and data fetched during server-side rendering even when a normal /admin request returns 401.
Are non-page routes affected by the described bypass?
The described behavior applies to page routes: Nuxt renders the page using the normalized path, while Nitro routing, route rules, and server middleware receive the original leading-slash path. The provided information does not describe the same bypass for other route types.