apache 2 proxypassreverse appends virtualhost port - apache

I have been trying to setup a reverse proxy using apache 2 mod_proxy and the proxypass & proxypassreverse directives.
I am installing WSO2 Identity Server and wish to access that app using a url such as the following .
hxxp://myserver.domain.com/wso2/
The myserver.domain.com is accessible on the internet
Internally on my network I have set up a virtualhost running in my apache2 configuration with the following parameters:
For various reasons, port 80 is unavailable and the virtualhost must stay as :8080.
Finally, here is my virtual host configuration
<VirtualHost *:8080>
<Location /wso2/>
ProxyPass hxxps://internal.wso2.node:9443/
ProxyPassReverse hxxs://internal.wso2.node:9443/
</Location>
ProxyVia On
ProxyPreserveHost Off
ProxyAddHeaders Off
ProxyRequests Off
SSLProxyEngine On
SSLProxyCheckPeerCN Off
</VirtualHost>
The issue:
I can use my web browser ( Firefox/Chrome) to request the http://myserver.domain.com/wso2/ resource. In my log files I see that the request does hit the apache server and the virtualhost catches the /wso2/ location.
It passes through the proxy and lands on the internal.wso2.node server. however, the product WSO2 IS preforms several redirects which, in the log files I see it requesting the resource with the port appended.
Here is the request flow
hxxp://myserver.domain.com/wso2/ -> hxxps://internal.wso2.node:9443/
REDIRECT x3
hxxps://internal.wso2.node:8080/carbon ->
hxxps://internal.wso2.node:8080/carbon/admin/login.jsp
Back to my web browser
hxxp://myserver.domain.com:8080/wso2/carbon/admin/login.jsp
For some reason the apache response back appends its virtual host to the url I am requesting.
If I remove the port:8080 and request again the full url it will access the resource fine. However any attempt to access using only http://myserver.domain.com/wso2/ will result in redirects and the port appended.

As per covener's suggestion the culprit in this case proved to be the following directives:
UseCanonicalName Off
UseCanonicalPhysicalPort Off
Additionally, the web app I am trying to access makes use of sessions and cookies, therefore we must also proxy those, see the added directives under the ProxyPass & ProxyPassReverse.
Therefore the updated virtualhost configuration file should now look like this
<VirtualHost *:8080>
ServerName: myServer.domain.com
UseCanonicalName Off
UseCanonicalPhysicalPort Off
<Location /wso2/>
ProxyPass hxxps://internal.wso2.node:9443/
ProxyPassReverse hxxs://internal.wso2.node:9443/
ProxyPassReverseCookiePath / /wso2/
ProxyPassReverseCookieDomain internal.wso2.node myserver.domain.com
</Location>
ProxyVia On
ProxyPreserveHost Off
ProxyAddHeaders Off
ProxyRequests Off
SSLProxyEngine On
SSLProxyCheckPeerCN Off
</VirtualHost>

Related

Apache24 how to proxy and return 404 for undefined endpoints

I have two virtual hosts running on a single Tomcat server. Lets call them a.com and b.com. Tomcat is configured to support only http on port 8080. (This is simplified, in real life there are multiple Tomcat instances each running a set of virtual hosts.)
I am fronting the host with Apache24 for the purpose of proxying incoming https requests to backend http. This emulates a production environment in which https certificates are handled by a corporate firewall, and requests are forwarded to the backend via http with some additional header fields inserted.
So, I have this proxying for restricted (external) users with two-way authentication:
https://a.com:443 -> http://a.com:8080
I also have this proxying for trusted (internal) users:
http://a.com:80 -> http://a.com:8080
http://b.com:80 -> http://b.com:8080
The problem is that due to some Apache24 default handling, a request to https://b.com/foo gets routed to http://a.com:8080/foo. I want to the https to b.com to return a 404! I know I need some default mappings to kill the b.com request but so far nothing has worked.
The Apache24 details:
File httpd-vhosts.conf:
<VirtualHost a.com:80>
ProxyPreserveHost On
ProxyRequests Off
ServerName a.com
DocumentRoot "c:/tmp"
ProxyPass / http://a.com:8080/
ProxyPassReverse / http://a.com:8080/
Header set Access-Control-Allow-Origin "*"
</VirtualHost>
<VirtualHost b.com:80>
ProxyPreserveHost On
ProxyRequests Off
ServerName b.com
DocumentRoot "c:/tmp"
ProxyPass / http://b.com:8080/
ProxyPassReverse / http://b.com:8080/
Header set Access-Control-Allow-Origin "*"
</VirtualHost>
File httpd-ssl/conf:
<VirtualHost a.com:443>
ProxyPreserveHost On
ProxyRequests Off
SSLEngine On
ServerName a.com
SSLVerifyClient require
SSLVerifyDepth 2
SSLStrictSNIVHostCheck on
#RewriteEngine On
RequestHeader set X-Forwarded-Proto https
RequestHeader setifempty CUSTOMFIELD "expr=CN=%{SSL_CLIENT_S_DN_CN}"
ProxyPass / http://a.com:8080/
ProxyPassReverse / http://a.com:8080/
SSLCertificateFile "c:/certs/a.com.crt"
SSLCertificateKeyFile "c:/certs/a.com.key"
SSLCACertificateFile "c:/certs/ca.crt"
</VirtualHost>
I see in the Apache24 logs lines that start like this when I request https://b.com/foo:
mod_proxy.c(880): [client 127.0.0.1:57956] AH03461: attempting to match URI path '/foo' against prefix '/' for proxying
mod_proxy.c(997): [client 127.0.0.1:57956] AH03464: URI path '/foo' matches proxy handler 'proxy:http://a.com:8080/foo'

ProxyPassReverse does not keep correct protocol while redirecting

I have set up a Virtuoso server that serves Linked Data using content negotiation. The server is served through a reverse proxy Apache server and may be queried using http or https.
http://public.server.org/myapp --> http://private.local.domain:1234/
https://public.server.org/myapp --> http://private.local.domain:1234/
The Virtuoso server then performs content negotiation and redirects to /describe?...
I have no problem when accessing the public server through http. The redirection takes place and content is retrieved.
However, when I access the public server though https, the redirection sends me to http://public.server.org/describe?... (that is HTTP, not HTTPS).
I'm expecting to be redirected to https://public.server.org/describe?... (with the same protocol as the original query).
My configuration is:
<VirtualHost xxx.yyy.zzz.ttt:80>
ServerName public.server.org
ProxyPass /myapp http://localhost:8890/myapp
ProxyPassReverse /myapp http://localhost:8890/myapp
ProxyRequests Off
<Location /describe>
ProxyPass http://localhost:8890/describe
ProxyPassReverse /describe
</Location>
</VirtualHost>
<VirtualHost xxx.yyy.zzz.ttt:443>
ServerName public.server.org
ProxyPass /myapp http://localhost:8890/myapp
ProxyPassReverse /myapp http://localhost:8890/myapp
ProxyRequests Off
<Location /describe>
ProxyPass http://localhost:8890/describe
ProxyPassReverse /describe
</Location>
</VirtualHost>
Is it possible for apache to correctly reverse the proxy in order to maintain the original query protocol while redirecting?
After debugging with dumpio and Apache error logs, I think I found the problem.
What happened?
First, my configuration was incorrect. At another place I did not transcribe here, I had a ProxyPreserveHost On directive that was active. Hence, the configuration worked but for wrong reasons.
Apache was keeping the Host and Virtuoso used this host. Hence, when sending a redirect to /describe..., Virtuoso was redirecting to http://public.server.org/describe... instead of my expected http://localhost:8890/describe...
Hence, the redirection was not captured by the ProxyPassReverse directives and passed unchanged to the client (and it worked). The problem being that the redirection was always done through http, regardless of the original query scheme.
Solution
I decided to drop the ProxyPreserveHost On directive and rely on a correct ProxyPassReverse directive.
For an unknown reason, I could not figure out the correct setting inside the Location, hence I used the settings:
<VirtualHost xxx.yyy.zzz.ttt:443>
ServerName public.server.org
ProxyPass /myapp http://localhost:8890/myapp
ProxyPassReverse /myapp http://localhost:8890/myapp
ProxyRequests Off
ProxyPreserveHost Off # To avoid problems if it is set On elsewhere.
ProxyPass /describe http://localhost:8890/describe
ProxyPassReverse /describe http://localhost:8890/describe
</VirtualHost>
Note: I only changed the https settings as the http ones were functioning somehow (hence the http virtualhost still uses ProxyPreserveHost On and no ProxyPassReverse

Reverse proxy an http:// domain to a GitHub Pages URL

I have a URL, http://example.com, that I would like to use to serve content from my GitHub Pages site at https://myusername.github.io/mysite/ via a reverse proxy in Apache. This is both as a temporary workaround until I update example.com's DNS setting to point to GitHub Pages, as well as to teach myself how reverse proxies work.
I have my Apache config like so:
<VirtualHost *:80>
ServerName example.com
SSLEngine On
SSLProxyEngine On
SSLProxyVerify none
SSLProxyCheckPeerCN off
ProxyPass "/" "https://myusername.github.io/mysite/"
</VirtualHost>
When I try to go to "example.com", I get "The proxy server could not handle the request GET /.
Reason: Error during SSL Handshake with remote server."
Is what I'm trying to do possible, and if so, what should I be changing?
I'm using Apache 2.2.
You should probably remove the line:
SSLEngine On
It enables HTTPS on your port 80... but you don't provide an SSL certificate (...and HTTPS uses port 443).
You should also add the line:
ProxyPassReverse "/" "https://myusername.github.io/mysite/"
The following config works perfectly on reverse proxy github pages
<VirtualHost *:80>
ServerName custom-domain
ServerAdmin encycode#gmail.com
ProxyRequests Off
ProxyPreserveHost On
SSLProxyEngine on
SSLProxyVerify none
SSLProxyCheckPeerCN off
SSLProxyCheckPeerName off
SSLProxyCheckPeerExpire off
RequestHeader set Host "myusername.github.io"
RequestHeader set X-Forwarded-Proto https
RequestHeader set Origin "myusername.github.io"
ProxyPass / https://myusername.github.io/mysite/
ProxyPassReverse / https://myusername.github.io/mysite/
</VirtualHost>
Make sure you replace myusername with your github username, mysite with your github repo name and custom-domain with your custom url
You don't have to implement a reverse proxy yourself, since Github allows you to specify a custom domain
https://docs.github.com/en/pages/configuring-a-custom-domain-for-your-github-
pages-site

httpd reverse proxy redirect with extra root directory name

I deploy a website war in wildfly named testDom-0.1 with apache httpd reverse proxy on. After logging in successfully, the default successful URL in spring security is "/booking", but the browser always get "testDom-0.1/booking" and then complain 404 error, if manually change the url into /booking, the page can be accessed without problem.
http.formLogin()
.loginPage("/denglu").permitAll()
.defaultSuccessUrl("/booking",true)
<VirtualHost *:80>
ProxyRequests off
ProxyPreserveHost On
ProxyPass / http://127.0.0.1:8080/testDom-0.1/
ProxyPassReverse / http://127.0.0.1:8080/testDom-0.1/
ProxyPassReverseCookiePath /testDom-0.1 /
<proxy>
Order deny,allow
Allow from all
</proxy>
</VirtualHost>
The expected return url should be localhost/booking not localhost/testDom-0.1/booking

ProxyPass with a port in Apache Virtualhost does not work

I'm using WSO2 API Manager. I have fronted API Manager(tomcat) with an Apache HTTP Server.
For the URL api.abc.xyz.lk a public IP has been assigned. For that public IP a local IP which is 192.168.6.162 has been assigned. I have added a virtual-host to redirect all the http://api.abc.xyz.lk to http://192.168.6.162:9763/store.
What I'm trying to do here is redirect all the http://api.abc.xyz.lk requests to http://192.168.6.162:9763/store.
Below is the virtual-host block I use.
<Virtualhost *:80>
ServerName api.abc.xyz.lk
ServerAlias api.abc.xyz.lk
ProxyPreserveHost On
ProxyRequests Off
ProxyPass / http://192.168.6.162:9763/store
ProxyPassReverse / http://192.168.6.162:9763/store
</Virtualhost>
The problem is
the URL that works is as below
http://api.abc.xyz.lk:9763/store
But actually what I want is
http://api.abc.xyz.lk
How can I fix this?
you need to modify this proxy pass
ProxyPass /store http://192.168.6.162:9763/store
ProxyPassReverse /store http://192.168.6.162:9763/store
this will do the trick..
make sure to enable the proxy ports in server, you can configure proxy ports by editing "catalina-server.xml" in $UES_HOME/repository/conf/tomcat/catalina-server.xml