-
Notifications
You must be signed in to change notification settings - Fork 386
Description
Is your feature request related to a problem? Please describe.
We are using nginx-ingress
with the nginx.ingress.kubernetes.io/auth-url
annotation.
We want to apply an access rule to this URL: https://admin.site.example/dashboard
We have an ingress config that looks like this:
ingress:
enabled: true
annotations:
kubernetes.io/ingress.class: nginx
nginx.ingress.kubernetes.io/auth-url: "http://oathkeeper.site.example/decisions$request_uri"
nginx.ingress.kubernetes.io/auth-response-headers: Authorization
Oathkeeper expects (correct me if I'm wrong) a request that looks like this:
GET /decisions/dashboard HTTP/2
Host: admin.site.example
Oathkeeper will actually receive:
GET /decisions/dashboard HTTP/2
Host: oathkeeper.site.example
The default nginx-ingress template generates an NGINX config where the Host
header sent to Oathkeeper is the auth_request host oathkeeper.site.example
instead of our target host admin.site.example
:
Generated nginx-ingress config
## start server admin.site.example
server {
server_name admin.site.example ;
listen 80 proxy_protocol ;
listen 443 proxy_protocol proxy_protocol ssl http2 ;
set $proxy_upstream_name "-";
ssl_certificate_by_lua_block {
certificate.call()
}
location = /_external-auth-Lw {
internal; # ngx_auth_request module overrides variables in the parent request,
# therefore we have to explicitly set this variable again so that when the parent request
# resumes it has the correct value set for this variable so that Lua can pick backend correctly
set $proxy_upstream_name "example-site-admin-web-80";
proxy_pass_request_body off;
proxy_set_header Content-Length "";
proxy_set_header X-Forwarded-Proto "";
proxy_set_header X-Request-ID $req_id;
proxy_set_header Host oathkeeper.site.example;
proxy_set_header X-Original-URL $scheme://$http_host$request_uri;
proxy_set_header X-Original-Method $request_method;
proxy_set_header X-Sent-From "nginx-ingress-controller";
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $remote_addr;
proxy_set_header X-Auth-Request-Redirect $request_uri;
proxy_buffering off;
proxy_buffer_size 4k;
proxy_buffers 4 4k;
proxy_request_buffering on;
proxy_http_version 1.1;
proxy_ssl_server_name on;
proxy_pass_request_headers on;
# Pass the extracted client certificate to the auth provider
proxy_set_header Host "admin.site.example";
set $target http://oathkeeper.site.example/decisions$request_uri;
proxy_pass $target;
}
location / {
set $namespace "example-site-admin";
set $ingress_name "example-site-admin-web";
set $service_name "example-site-admin-web";
set $service_port "80";
set $location_path "/"; rewrite_by_lua_block {
lua_ingress.rewrite({
force_ssl_redirect = false,
ssl_redirect = true,
force_no_ssl_redirect = false,
use_port_in_redirects = false,
})
balancer.rewrite()
plugins.run()
}
# be careful with `access_by_lua_block` and `satisfy any` directives as satisfy any
# will always succeed when there's `access_by_lua_block` that does not have any lua code doing `ngx.exit(ngx.DECLINED)`
# other authentication method such as basic auth or external auth useless - all requests will be allowed.
#access_by_lua_block {
#}
header_filter_by_lua_block {
lua_ingress.header()
plugins.run()
}
body_filter_by_lua_block {
}
log_by_lua_block {
balancer.log()
monitor.call()
plugins.run()
}
port_in_redirect off; set $balancer_ewma_score -1;
set $proxy_upstream_name "example-site-admin-web-80";
set $proxy_host $proxy_upstream_name;
set $pass_access_scheme $scheme;
set $pass_server_port $proxy_protocol_server_port;
set $best_http_host $http_host;
set $pass_port $pass_server_port;
set $proxy_alternative_upstream_name "";
# this location requires authentication
auth_request /_external-auth-Lw;
auth_request_set $auth_cookie $upstream_http_set_cookie;
add_header Set-Cookie $auth_cookie;
auth_request_set $authHeader0 $upstream_http_authorization;
proxy_set_header 'Authorization' $authHeader0;
proxy_set_header Host $best_http_host;
# Allow websocket connections
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
proxy_set_header X-Request-ID $req_id;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $remote_addr;
proxy_set_header X-Forwarded-Host $best_http_host;
proxy_set_header X-Forwarded-Port $pass_port;
proxy_set_header X-Forwarded-Proto $pass_access_scheme;
proxy_set_header X-Scheme $pass_access_scheme;
# Pass the original X-Forwarded-For
proxy_set_header X-Original-Forwarded-For $http_x_forwarded_for;
# mitigate HTTPoxy Vulnerability
# https://www.nginx.com/blog/mitigating-the-httpoxy-vulnerability-with-nginx/
proxy_set_header Proxy "";
# Custom headers to proxied server
proxy_connect_timeout 5s;
proxy_send_timeout 60s;
proxy_read_timeout 60s;
proxy_buffering off;
proxy_buffer_size 4k;
proxy_buffers 4 4k;
proxy_max_temp_file_size 1024m;
proxy_request_buffering on;
proxy_http_version 1.1;
proxy_cookie_domain off;
proxy_cookie_path off;
# In case of errors try the next upstream server before returning an error
proxy_next_upstream error timeout;
proxy_next_upstream_timeout 0;
proxy_next_upstream_tries 3;
proxy_pass http://upstream_balancer;
proxy_redirect off;
}
}
## end server admin.site.example
Describe the solution you'd like
I would like to be able to point the auth-url
annotation at Oathkeeper and have everything work without changing any internal nginx-ingress config templates.
Describe alternatives you've considered
The default template includes all the normal X-Forwarded-* headers. It may work out-of-the-box with the /decisions/traefik
endpoint added in #486 , but I'm not sure if this is released yet.
Additional context
oryd/oathkeeper:v0.38.3-beta.1
quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.32.0