Issue
I'd like to configure Apache as a reverse proxy for that determines the URL to proxy to dynamically by parsing the path of the requested URL.
For example, the URL http://proxy-server/app/your-app
would get proxied to http://your-app:8000/
and http://proxy-server/app/your-app/some/path
would go to http://your-app:8000/some/path
.
The problem I'm running into with the below configuration is that http://proxy-server/app/your-app/
works just fine, but http://proxy-server/app/your-app/some/path
gets redirected to http://proxy-server/some/path
, which gives a 404 error.
I've tried using just mod_proxy
like this
ProxyPassMatch "^/app/([^/]+)(?:/(.*))?$" "http://$1:8000/$2"
And I've tried it with mod_rewrite
RewriteEngine On
RewriteBase "/app/"
RewriteRule "^([^/]+)/?$" "http://$1:8000/" [E=CONTAINER:$1,P]
RewriteRule "^([^/]+)/(.+)$" "http://$1:8000/$2" [E=CONTAINER:$1,P]
ProxyPassInterpolateEnv On
ProxyPassReverse "/app/" "http://${CONTAINER}:8000/" interpolate
When I curl -D - http://proxy-server/app/your-app
I get an HTTP/1.1 200 OK
response. When I curl -D - http://proxy-server/app/your-app/some/path
I get a HTTP/1.1 301 Move Permanently
response with Location: /some/path/
.
I'm not sure where the 301 is coming from. Neither Apache nor the app running on that host should be returning a 301, but the Location
header made me think it might be that the reverse proxy isn't set up to correctly rewrite URLs from the remote to which it is proxying, which is why I added the ProxyPassReverse
directive above. But I still can't get it working.
Any insight into how to set this up would be greatly appreciated.
Solution
I did have the ProxyPassReverse
directive configured incorrectly for this scenario.
The remote server to which I was proxying (a Django app) was issuing redirects by setting the Location
header to a path, not a full URL. So I had to configure Apache like this:
RewriteEngine On
RewriteRule "^/app/([^/]+)(?:/.*)?$" - [E=CONTAINER:$1]
ProxyPassInterpolateEnv On
ProxyPass "/app/${CONTAINER}/" "http://${CONTAINER}:8000/" interpolate
ProxyPassReverse "/app/${CONTAINER}/" "http://${CONTAINER}:8000/" interpolate
# This guarantees that any Location headers that are just absolute paths
# get rewritten
ProxyPassReverse "/app/${CONTAINER}/" "/" interpolate
That last line is the key. It tells Apache that if it gets a Location: /some/path/
header, it should rewrite it as Location: /app/your-app/some/path/
. The first ProxyPassReverse
directive would have triggered only if Apache had received Location: http://${CONTAINER}:8000/some/path/
.
Answered By - darth_mall Answer Checked By - Willingham (PHPFixing Volunteer)
0 Comments:
Post a Comment
Note: Only a member of this blog may post a comment.