Summary
The HTTP script loader builds its http.Client with no CheckRedirect policy, so custom headers set via WithHeaderAuth(...) (e.g. X-API-Key) are re-sent on redirects to any host. Go's stdlib strips Authorization, Cookie, and WWW-Authenticate on cross-host redirects but does not strip arbitrary custom headers, so a configured API key can leak to a redirect target the operator never intended.
Root cause
platform/script/loader/fromHTTP.go: NewFromHTTPWithOptions (~L194-226) constructs the client without setting CheckRedirect, and GetReader (~L234-275) applies the configured Authenticator headers to the initial request. Default redirect handling then replays the custom headers on every hop.
Reproduction (confirmed)
Loader configured with WithHeaderAuth(map[string]string{"X-API-Key": "SECRET123"}), fetching https://scripts.example.com/x.risor. The host returns 302 → https://attacker.example/. The client re-sends X-API-Key: SECRET123 to attacker.example. In the same run, an Authorization header set via WithBearerAuth was stripped by Go — only the custom header leaked.
Trigger vectors: a compromised or malicious script host, a MITM on a plain-http URL, or a compromised CDN in front of the origin.
Impact
High — credential disclosure. Any caller using WithHeaderAuth (the documented way to pass API keys to a script endpoint) can leak that key to any host the endpoint redirects to.
Fix
Set client.CheckRedirect to drop auth and custom headers when the redirect target host differs from the original, or refuse cross-host redirects. Equivalently, re-apply the Authenticator only on same-origin redirects and strip the headers it added on cross-origin hops. Add tests asserting the custom header is absent on a cross-host redirect and present on a same-host one.
Summary
The HTTP script loader builds its
http.Clientwith noCheckRedirectpolicy, so custom headers set viaWithHeaderAuth(...)(e.g.X-API-Key) are re-sent on redirects to any host. Go's stdlib stripsAuthorization,Cookie, andWWW-Authenticateon cross-host redirects but does not strip arbitrary custom headers, so a configured API key can leak to a redirect target the operator never intended.Root cause
platform/script/loader/fromHTTP.go:NewFromHTTPWithOptions(~L194-226) constructs the client without settingCheckRedirect, andGetReader(~L234-275) applies the configuredAuthenticatorheaders to the initial request. Default redirect handling then replays the custom headers on every hop.Reproduction (confirmed)
Loader configured with
WithHeaderAuth(map[string]string{"X-API-Key": "SECRET123"}), fetchinghttps://scripts.example.com/x.risor. The host returns302→https://attacker.example/. The client re-sendsX-API-Key: SECRET123toattacker.example. In the same run, anAuthorizationheader set viaWithBearerAuthwas stripped by Go — only the custom header leaked.Trigger vectors: a compromised or malicious script host, a MITM on a plain-
httpURL, or a compromised CDN in front of the origin.Impact
High — credential disclosure. Any caller using
WithHeaderAuth(the documented way to pass API keys to a script endpoint) can leak that key to any host the endpoint redirects to.Fix
Set
client.CheckRedirectto drop auth and custom headers when the redirect target host differs from the original, or refuse cross-host redirects. Equivalently, re-apply theAuthenticatoronly on same-origin redirects and strip the headers it added on cross-origin hops. Add tests asserting the custom header is absent on a cross-host redirect and present on a same-host one.