Why
Cross-origin redirects are the source of axios's last four merged security CVEs. Native fetch follows redirects automatically and preserves Authorization/Cookie/proxy headers — leaking creds to whoever the upstream redirects you to (cloud metadata, attacker-controlled domains, …).
We need a beforeRedirect hook and a default header allowlist policy.
Evidence
- axios PR #10660 — "unrestricted cloud metadata exfiltration via header injection chain" (CVE).
- axios PR #10779 — "more header pollutions".
- axios PR #10794 — "clear stale header on redirect when target is no-proxy".
- axios PR #10800 — "close redirect listener chain correctly".
- got
source/core/options.ts:921, 2250 — strips host/cookie/auth on cross-origin redirect, exposes beforeRedirect hook for app-specific rules.
Implementation challenge
Native fetch does not expose redirect events. To intercept, we set redirect: 'manual' and follow redirects ourselves. This is a non-trivial cost — but it's the only correct option once we care about security.
Proposal
hooks: {
beforeRedirect?: MaybeArray<(ctx: RedirectContext) => void | Request | Promise<…>>
}
config: {
redirect?: 'follow' | 'manual' | 'error'
redirectSafeHeaders?: string[] // default: ['accept', 'accept-encoding', 'accept-language', 'user-agent']
redirectMaxCount?: number // default: 5
redirectAllowDowngrade?: boolean // default: false (https → http blocked)
}
Defaults
- Cross-origin redirect → drop everything except
redirectSafeHeaders (default: 4 above).
- Same-origin redirect → preserve all headers.
https → http redirect → throw unless redirectAllowDowngrade: true.
beforeRedirect hook fires after stripping but before next request — escape hatch.
Out of scope
Why
Cross-origin redirects are the source of axios's last four merged security CVEs. Native
fetchfollows redirects automatically and preservesAuthorization/Cookie/proxy headers — leaking creds to whoever the upstream redirects you to (cloud metadata, attacker-controlled domains, …).We need a
beforeRedirecthook and a default header allowlist policy.Evidence
source/core/options.ts:921, 2250— stripshost/cookie/auth on cross-origin redirect, exposesbeforeRedirecthook for app-specific rules.Implementation challenge
Native fetch does not expose redirect events. To intercept, we set
redirect: 'manual'and follow redirects ourselves. This is a non-trivial cost — but it's the only correct option once we care about security.Proposal
Defaults
redirectSafeHeaders(default: 4 above).https → httpredirect → throw unlessredirectAllowDowngrade: true.beforeRedirecthook fires after stripping but before next request — escape hatch.Out of scope
Linkheader: see #pagination issue (separate).