nginx proxy_pass rewrite of response header location
The aim of this nginx instance is to get GitLab and OpenWRT Luci to redirect through a reverse proxy. It's already working for several other websites, all which have a base url which seems to counter this issue.
- GitLab in this example is on the local server at port 9000.
- The nginx website is on port 8080.
- OpenWRT has the exact same issue, but with /cgi-bin/luci/
The relevant nginx config for the example location is;
location /gitlab/ {
proxy_pass http://127.0.0.1:9000/;
proxy_redirect default;
}
- Note that the results are the same with and without a trailing slash.
There are some header proxy configuration options being applied to this location.
# Timeout if the real server is dead
proxy_next_upstream error timeout invalid_header http_500 http_502 http_503;
# Basic Proxy Config
proxy_set_header Host $host:$server_port;
proxy_set_header Origin $scheme://$host:$server_port;
proxy_set_header Connection $http_connection;
proxy_set_header Cookie $http_cookie;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header X-Forwarded-Protocol $scheme;
proxy_set_header X-Scheme $scheme;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Ssl on;
proxy_set_header X-Frame-Options SAMEORIGIN;
# Advanced Proxy Config
send_timeout 5m;
proxy_read_timeout 300;
proxy_send_timeout 300;
proxy_connect_timeout 300;
proxy_buffers 32 4k;
proxy_buffer_size 4k;
proxy_busy_buffers_size 64k;
proxy_temp_file_write_size 64k;
proxy_http_version 1.1;
proxy_cache_bypass $cookie_session;
proxy_no_cache $cookie_session;]
- Commenting out #proxy_set_header Host instead redirects the browser to
https://127.0.0.1:9000/users/sign_in
When browsing to https://website.com:8080/gitlab/
;
GET /gitlab/ HTTP/1.1
Host: website.com:8080
The response incorrectly goes back to /users/sign_in
instead of /gitlab/users/sign_in
HTTP/1.1 302 Found
Cache-Control: no-cache
Connection: keep-alive
Content-Type: text/html; charset=utf-8
Location: https://website.com:8080/users/sign_in
Browsing manually to https://website:8080/gitlab/users/sign_in loads the page, but no assets as they fall until the same issue as above.
Reading nginx docs, it suggests that the default proxy behaviour should handle this scenario, though it seems to fail.
The logs don't seem to show much.
What additional steps should be taken to help diagnose why this might be happening?
Solution 1:
Add a trailing slash to your proxy_pass
target.
Update : The OP didn't precise the vhost was accepting https
. As the scheme is forwarded to the backend server with additionnal headers, then an issue occurs since proxy_redirect default;
orders nginx to expect http scheme by default when rewriting Location
headers in upstream replies, instead of https.
So, this had to be changed explicitely to a more generic form (the trailing slash is still necessary) :
location /gitlab/ {
proxy_pass http://127.0.0.1:9000/;
proxy_redirect $scheme://$host:$server_port/ /gitlab/;
}