From 2b05c9042816c2f1a2f5ec12b4a169a42eabea1c Mon Sep 17 00:00:00 2001 From: Cole Mickens Date: Sun, 29 Jan 2017 13:52:50 -0800 Subject: [PATCH] add signin url req support --- .../rootfs/etc/nginx/template/nginx.tmpl | 8 +++++ core/pkg/ingress/annotations/authreq/main.go | 26 +++++++++++------ .../ingress/annotations/authreq/main_test.go | 29 +++++++++++-------- 3 files changed, 42 insertions(+), 21 deletions(-) diff --git a/controllers/nginx/rootfs/etc/nginx/template/nginx.tmpl b/controllers/nginx/rootfs/etc/nginx/template/nginx.tmpl index 4684a497c..248805718 100644 --- a/controllers/nginx/rootfs/etc/nginx/template/nginx.tmpl +++ b/controllers/nginx/rootfs/etc/nginx/template/nginx.tmpl @@ -245,6 +245,8 @@ http { {{ end }} {{ if not (empty $location.ExternalAuth.Method) }} proxy_method {{ $location.ExternalAuth.Method }}; + proxy_set_header X-Original-URI $request_uri; + proxy_set_header X-Scheme $pass_access_scheme; {{ end }} proxy_set_header Host $host; proxy_pass_request_headers on; @@ -269,6 +271,10 @@ http { # this location requires authentication auth_request {{ $authPath }}; {{ end }} + + {{ if not (empty $location.ExternalAuth.SigninURL) }} + error_page 401 = {{ $location.ExternalAuth.SigninURL }}; + {{ end }} {{ if (and (not (empty $server.SSLCertificate)) $location.Redirect.SSLRedirect) }} # enforce ssl on server side @@ -316,6 +322,8 @@ http { proxy_set_header X-Forwarded-Host $host; proxy_set_header X-Forwarded-Port $pass_port; proxy_set_header X-Forwarded-Proto $pass_access_scheme; + proxy_set_header X-Original-URI $request_uri; + proxy_set_header X-Scheme $pass_access_scheme; # mitigate HTTPoxy Vulnerability # https://www.nginx.com/blog/mitigating-the-httpoxy-vulnerability-with-nginx/ diff --git a/core/pkg/ingress/annotations/authreq/main.go b/core/pkg/ingress/annotations/authreq/main.go index 622d74540..c5659447a 100644 --- a/core/pkg/ingress/annotations/authreq/main.go +++ b/core/pkg/ingress/annotations/authreq/main.go @@ -25,16 +25,18 @@ import ( const ( // external URL that provides the authentication - authURL = "ingress.kubernetes.io/auth-url" - authMethod = "ingress.kubernetes.io/auth-method" - authBody = "ingress.kubernetes.io/auth-send-body" + authURL = "ingress.kubernetes.io/auth-url" + authSigninURL = "ingress.kubernetes.io/auth-signin" + authMethod = "ingress.kubernetes.io/auth-method" + authBody = "ingress.kubernetes.io/auth-send-body" ) // External returns external authentication configuration for an Ingress rule type External struct { - URL string `json:"url"` - Method string `json:"method"` - SendBody bool `json:"sendBody"` + URL string `json:"url"` + SigninURL string `json:"signinUrl"` + Method string `json:"method"` + SendBody bool `json:"sendBody"` } var ( @@ -70,6 +72,11 @@ func (a authReq) Parse(ing *extensions.Ingress) (interface{}, error) { return nil, err } + signin, err := parser.GetURLAnnotation(authSigninURL, ing) + if err != nil { + return nil, err + } + m, err := parser.GetStringAnnotation(authMethod, ing) if err != nil { return nil, err @@ -82,8 +89,9 @@ func (a authReq) Parse(ing *extensions.Ingress) (interface{}, error) { sb, _ := parser.GetBoolAnnotation(authBody, ing) return &External{ - URL: auth.String(), - Method: m, - SendBody: sb, + URL: auth.String(), + SigninURL: signin.String(), + Method: m, + SendBody: sb, }, nil } diff --git a/core/pkg/ingress/annotations/authreq/main_test.go b/core/pkg/ingress/annotations/authreq/main_test.go index 696d8bdc0..75cd6d2b7 100644 --- a/core/pkg/ingress/annotations/authreq/main_test.go +++ b/core/pkg/ingress/annotations/authreq/main_test.go @@ -67,23 +67,25 @@ func TestAnnotations(t *testing.T) { ing.SetAnnotations(data) tests := []struct { - title string - url string - method string - sendBody bool - expErr bool + title string + url string + signinURL string + method string + sendBody bool + expErr bool }{ - {"empty", "", "", false, true}, - {"no scheme", "bar", "", false, true}, - {"invalid host", "http://", "", false, true}, - {"invalid host (multiple dots)", "http://foo..bar.com", "", false, true}, - {"valid URL", "http://bar.foo.com/external-auth", "", false, false}, - {"valid URL - send body", "http://foo.com/external-auth", "POST", true, false}, - {"valid URL - send body", "http://foo.com/external-auth", "GET", true, false}, + {"empty", "", "", "", false, true}, + {"no scheme", "bar", "bar", "", false, true}, + {"invalid host", "http://", "http://", "", false, true}, + {"invalid host (multiple dots)", "http://foo..bar.com", "http://foo..bar.com", "", false, true}, + {"valid URL", "http://bar.foo.com/external-auth", "http://bar.foo.com/external-auth", "", false, false}, + {"valid URL - send body", "http://foo.com/external-auth", "http://foo.com/external-auth", "POST", true, false}, + {"valid URL - send body", "http://foo.com/external-auth", "http://foo.com/external-auth", "GET", true, false}, } for _, test := range tests { data[authURL] = test.url + data[authSigninURL] = test.signinURL data[authBody] = fmt.Sprintf("%v", test.sendBody) data[authMethod] = fmt.Sprintf("%v", test.method) @@ -101,6 +103,9 @@ func TestAnnotations(t *testing.T) { if u.URL != test.url { t.Errorf("%v: expected \"%v\" but \"%v\" was returned", test.title, test.url, u.URL) } + if u.SigninURL != test.signinURL { + t.Errorf("%v: expected \"%v\" but \"%v\" was returned", test.title, test.signinURL, u.SigninURL) + } if u.Method != test.method { t.Errorf("%v: expected \"%v\" but \"%v\" was returned", test.title, test.method, u.Method) }