1
0
mirror of https://github.com/oauth2-proxy/oauth2-proxy.git synced 2025-06-15 00:15:00 +02:00

Strip X-Forwarded auth headers from whitelisted paths (#624)

* Strip X-Forwarded auth headers from whitelisted paths

For any paths that match skip-auth-regex, strip normal
X-Forwarded headers that would be sent based on pass-user-headers
or pass-access-token settings. This prevents malicious injecting
of authentication headers through the skip-auth-regex paths in
cases where the regex might be misconfigured and too open.
Control this behavior with --skip-auth-strip-headers flag. This
flag is set to TRUE by default (this is secure by default, but
potentially breaks some legacy configurations).

Only x-Forwarded headers stripped, left the Authorization header
untouched.

* Strip authorization header if it would be set

* Improve TestStripAuthHeaders test table

* Improve --skip-auth-strip-headers flag documentation
This commit is contained in:
Nick Meves
2020-07-14 15:46:44 -07:00
committed by GitHub
parent bb5977095f
commit abeb0236d8
5 changed files with 176 additions and 1 deletions

View File

@ -111,6 +111,7 @@ type OAuthProxy struct {
PreferEmailToUser bool
skipAuthRegex []string
skipAuthPreflight bool
skipAuthStripHeaders bool
skipJwtBearerTokens bool
mainJwtBearerVerifier *oidc.IDTokenVerifier
extraJwtBearerVerifiers []*oidc.IDTokenVerifier
@ -343,6 +344,7 @@ func NewOAuthProxy(opts *options.Options, validator func(string) bool) (*OAuthPr
whitelistDomains: opts.WhitelistDomains,
skipAuthRegex: opts.SkipAuthRegex,
skipAuthPreflight: opts.SkipAuthPreflight,
skipAuthStripHeaders: opts.SkipAuthStripHeaders,
skipJwtBearerTokens: opts.SkipJwtBearerTokens,
mainJwtBearerVerifier: opts.GetOIDCVerifier(),
extraJwtBearerVerifiers: opts.GetJWTBearerVerifiers(),
@ -718,7 +720,7 @@ func (p *OAuthProxy) ServeHTTP(rw http.ResponseWriter, req *http.Request) {
case path == p.RobotsPath:
p.RobotsTxt(rw)
case p.IsWhitelistedRequest(req):
p.serveMux.ServeHTTP(rw, req)
p.SkipAuthProxy(rw, req)
case path == p.SignInPath:
p.SignIn(rw, req)
case path == p.SignOutPath:
@ -891,6 +893,14 @@ func (p *OAuthProxy) AuthenticateOnly(rw http.ResponseWriter, req *http.Request)
rw.WriteHeader(http.StatusAccepted)
}
// SkipAuthProxy proxies whitelisted requests and skips authentication
func (p *OAuthProxy) SkipAuthProxy(rw http.ResponseWriter, req *http.Request) {
if p.skipAuthStripHeaders {
p.stripAuthHeaders(req)
}
p.serveMux.ServeHTTP(rw, req)
}
// Proxy proxies the user request if the user is authenticated else it prompts
// them to authenticate
func (p *OAuthProxy) Proxy(rw http.ResponseWriter, req *http.Request) {
@ -1122,6 +1132,30 @@ func (p *OAuthProxy) addHeadersForProxying(rw http.ResponseWriter, req *http.Req
}
}
// stripAuthHeaders removes Auth headers for whitelisted routes from skipAuthRegex
func (p *OAuthProxy) stripAuthHeaders(req *http.Request) {
if p.PassBasicAuth {
req.Header.Del("X-Forwarded-User")
req.Header.Del("X-Forwarded-Email")
req.Header.Del("X-Forwarded-Preferred-Username")
req.Header.Del("Authorization")
}
if p.PassUserHeaders {
req.Header.Del("X-Forwarded-User")
req.Header.Del("X-Forwarded-Email")
req.Header.Del("X-Forwarded-Preferred-Username")
}
if p.PassAccessToken {
req.Header.Del("X-Forwarded-Access-Token")
}
if p.PassAuthorization {
req.Header.Del("Authorization")
}
}
// CheckBasicAuth checks the requests Authorization header for basic auth
// credentials and authenticates these against the proxies HtpasswdFile
func (p *OAuthProxy) CheckBasicAuth(req *http.Request) (*sessionsapi.SessionState, error) {