14

I have an Apache web server that needs to reverse proxy a site. So example.com/test/ or example.com/test pull from the same other webserver. I have setup a reverse proxy for the one without the trailing slash like this:

ProxyPass /test http://othersite.com/test
ProxyPassReverse /test http://othersite.com/test

But it doesn't work with a trailing slash.

Any Ideas? I have tried redirecting from /test/ to /test with no luck.

Thanks.

3 Answers 3

23

Have you tried to rewrite the url?

RewriteEngine on 
RewriteRule ^/test$ /test/ [R]

ProxyRequests Off       
ProxyPreserveHost On

ProxyPass    /test/   http://othersite.com/test/
ProxyPassReverse /test/  http://othersite.com/test/
0
1

What do you mean it doesn't work with a trailing slash? Does it redirect to the wrong place? Does it give a 404 error? This is what I used to set up a reverse proxy and hide the source from the rest of the world.

ProxyRequests off
<Location /guides>
  ProxyPass http://blog.domain.com
  ProxyPassReverse http://blog.domain.com
  ProxyPassReverse /
  ProxyHTMLEnable On
  ProxyHTMLURLMap / /guides
  ProxyHTMLURLMap http://blogs.domain.com /guides
  RequestHeader unset Accept-Encoding
  RequestHeader set MySpecialHeader secretkey
  #LogLevel proxy:debug
</Location>

You can use this to test your proxy:

$ curl -I http://localhost:81/guides/top5
HTTP/1.1 301 Moved Permanently
Location: http://localhost:81/guides/top5/
1

You must either use trailing slashes on both arguments, or none.
Docs says should, not must, but I wouldn't be so benevolent as it just doesn't work well if you do.

If the first argument ends with a trailing /, the second argument should also end with a trailing /, and vice versa. Otherwise, the resulting requests to the backend may miss some needed slashes and do not deliver the expected results.
from: http://httpd.apache.org/docs/current/mod/mod_proxy.html#ProxyPass

This is what happens with various combinations:

ProxyPass "/aaa1/" "http://server2/mirror2/aaa2"

http://server1/aaa1 -> ERROR PAGE (expected, there is no file aaa1 and it's not proxied)
http://server1/aaa1/ -> WRONG (not server2): http://server1/mirror2/aaa2/

ProxyPass "/bbb1" "http://server2/mirror2/bbb2"

http://server1/bbb1 -> WRONG (not server2): http://server1/mirror2/bbb2/
http://server1/bbb1/ -> OK: address shows http://server1/bbb1/ but contents is from http://server2/mirror2/bbb2/

ProxyPass "/ccc1/" "http://server2/mirror2/ccc2/"

http://server1/ccc1 -> ERROR PAGE (expected, as above)
http://server1/ccc1/ -> OK: address shows http://server1/ccc1/ but contents is from http://server2/mirror2/ccc2/

ProxyPass "/ddd1" "http://server2/mirror2/ddd2/"

http://server1/ddd1 -> OK: address shows http://server1/ddd1/ but content is from http://server2/mirror2/ddd2/
http://server1/ddd1/ -> OK: address shows http://server1/ddd1/ but content is from http://server2/mirror2/ddd2/

Result:

If you want to proxy a dir, use trailing slash in both arguments. If a file, don't.

ddd is interesting, as it seems to work. It's possibly double slashing server2, which is OK on the filesystem, but it smells like trouble.

I can't find an explanation on behavior commented as WRONG. Path is from server2 as ordered by proxy, but it's opened on server1. Just a wild guess, Reverse Proxy (ProxyPass) is often used as a mirror/balancer, maybe it's a recovery attempt? When file mirror2/aaa2 is not found on server2, try to open it on server1?

@user59174 accepted answer is using trailing slashes on both arguments and that's why it's working.
But the reasoning is all wrong and that's confusing the slash issue even further.

The reason it works is not because of the rewrite.
Actually RewriteRule ^/test$ /test/ [R] does nothing at all on most servers, as that something done by default by a directive DirectorySlash On which is ON by default.
So unless there is DirectorySlash Off, all non-existing files are tried as a directory (slash is added)

Next, ProxyRequests Off if Off by default and has no effect on Reverse Proxy anyway.
ProxyPreserveHost On is about request header.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .