GHSA-p6jq-8vc4-79f6
Nuxt has Client-Side Path Traversal in Nuxt Island Payload Revival
Details
### Summary
A client-side path traversal vulnerability in Nuxt's Island payload revival mechanism allowed attackers to manipulate client-side requests to different endpoints within the same application domain when specific prerendering conditions are met.
### Technical Details
The vulnerability occurs in the client-side payload revival process (revive-payload.client.ts) where Nuxt Islands are automatically fetched when encountering serialized `__nuxt_island` objects. The issue affects the following flow:
1. During prerendering, if an API endpoint returns user-controlled data containing a crafted `__nuxt_island` object 2. This data gets serialized with `devalue.stringify` and stored in the prerendered page 3. When a client navigates to the prerendered page, `devalue.parse` deserializes the payload 4. The Island reviver attempts to fetch `/__nuxt_island/${key}.json` where `key` could contain path traversal sequences
### Prerequisites for Exploitation
This vulnerability requires **all** of the following conditions:
1. **Prerendered pages**: The application must use Nuxt's prerendering feature (`nitro.prerender`) 2. **Attacker-controlled API responses**: The attacker must be able to control the response content of an API endpoint that is called during prerendering via `useFetch`, `useAsyncData`, or similar composables 3. **Client-side navigation**: A user must navigate to the prerendered page (not during initial SSR hydration)
### Attack Scenario
```javascript // Malicious API response during prerendering { "__nuxt_island": { "key": "../../../../internal/service", "params": { "action": "probe" } } } ```
This could cause the client to make requests to `/__nuxt_island/../../../../internal/service.json` if path traversal is not properly handled by the server.
### Impact Assessment
- **Limited Impact**: The vulnerability has a low severity due to the highly specific prerequisites - **No Direct Data Exfiltration**: The vulnerability does not directly expose sensitive data - **Client-Side Only**: Requests originate from the client, not the server
### Mitigation
**Action Required:** - Update to Nuxt 3.19.0+ or 4.1.0+ immediately - Review any prerendered pages that fetch external or user-controlled data
**Temporary Workarounds** (if immediate update is not possible): 1. Disable prerendering for pages that fetch user-controlled data 2. Implement strict input validation on API endpoints used during prerendering 3. Use allowlists for API response structures during prerendering
### Fix Details
[The fix](https://github.com/nuxt/nuxt/commit/2566d2046bccb158d98fb13e42ce4b2c33fb2595) implemented validation for Island keys in `revive-payload.server.ts`: - Island keys must match the pattern `/^[a-z][a-z\d-]*_[a-z\d]+$/i` - Maximum length of 100 characters - Prevents path traversal and special characters
Are you affected?
Enter the version of the package you're using.