How to configure apache2 as reverse proxy as gateway for different turnkeys

digg_de's picture

Hi,

in the moment i use a turnkey lamp on my own vsphere enviroment. I have one static IP and connected my domain-name via DNS-A-Record to this IP and the turnkey lamp. Everything works fine.

Now i want to use a second turnkey lamp with a subdomain over the same IP. So i connected the new subdomain via DNS-A-Record to my static IP and the requests arrives on the 1st turnkey lamp. Now i enabled the proxy module on the 1st turnkey lamp and use the following configuration:

/etc/apache2/mods-enabled/proxy.conf:

ProxyRequests Off
<Proxy *>
    AddDefaultCharset off
    Order deny,allow
    Allow from all
</Proxy>
ProxyVia On

/etc/apache2/sites-available/default

NameVirtualHost subdomain.example.com:80
<VirtualHost subdomain.example.com:80>
    ServerName subdomain.example.com
    ProxyPass / http://192.168.2.12:80/
    ProxyPassReverse / http://192.168.2.12:80/
</VirtualHost>

NameVirtualHost subdomain.example.com:443
<VirtualHost subdomain.example.com:443>
    ServerName subdomain.example.com
    ProxyPass / https://192.168.2.12:443/
    ProxyPassReverse / https://192.168.2.12:443/
</VirtualHost>

NameVirtualHost *:80
<VirtualHost *:80>
    ServerName www.example.com
    Redirect permanent / https://www.example.com/
</VirtualHost>

NameVirtualHost *:443
<VirtualHost *:443>
    SSLEngine on
    SSLCertificateFile /var/ssl/www.example.com.crt
    SSLCertificateKeyFile /var/ssl/www.example.com.key
    SSLCACertificateFile /var/ssl/intermediate.crt
    ServerName www.example.com
    ServerAlias example.com
    DocumentRoot /var/www/
</VirtualHost>
...

/etc/hosts

127.0.0.1 localhost
127.0.1.1 lamp
192.168.2.8 www.example.com
192.168.2.12 subdomain.example.com

The apache-server starts without any error or warning, but the routing to the new turnkey lamp does not work? All requests to the subdomain are processed by the 1st turnkey lamp.

Can everybody help? What's wrong on my configuration?

Thanks!

digg_de's picture

The main problem is the SSL handshake. The first turnkey must handle the SSL handshake before any request will be processed. So i have changed the configuration:

/etc/apache2/sites-available/default:

NameVirtualHost *:80
<VirtualHost *:80>
        ServerName www.example.com
        Redirect permanent / https://www.example.com/
</VirtualHost>
<VirtualHost *:80>
        ServerName subdomain.example.com
        Redirect permanent / https://subdomain.example.com/
</VirtualHost>

NameVirtualHost *:443
<VirtualHost *:443>
        SSLEngine on
        SSLCertificateFile /var/ssl/www.example.com.crt
        SSLCertificateKeyFile /var/ssl/www.example.com.key
        SSLCACertificateFile /var/ssl/intermediate.crt
        ServerName www.example.com
        ServerAlias example.com
        DocumentRoot /var/www/admin-interface/public
</VirtualHost>
<VirtualHost *:443>
        SSLEngine on
        SSLCertificateFile /var/ssl/subdomain.example.com.crt
        SSLCertificateKeyFile /var/ssl/subdomain.example.com.key
        SSLCACertificateFile /var/ssl/intermediate.crt
        ServerName subdomain.example.com
        ProxyPass / https://192.168.2.12:443/
        ProxyPassReverse / https://192.168.2.12:443/
</VirtualHost>

Now the SSL handshake works, but now i got an error on the page:

Bad Request
Your browser sent a request that this server could not unterstand.

digg_de's picture

The problem was a usage of mod_rewrite definition outside the <virtualhost>. I moved it inside and everything works. Here the final configuration:

/etc/apache2/mods-enabled/proxy.conf (not neccessary to enable for reverse proxy):

#ProxyRequests Off
#<Proxy *>
#    AddDefaultCharset off
#    Order deny,allow
#    Allow from all
#</Proxy>
#ProxyVia On

/etc/apache2/sites-available/default

NameVirtualHost *:80
<VirtualHost *:80>
    ServerName www.example.com
    Redirect permanent / https://www.example.com/
</VirtualHost>
<VirtualHost *:80>
    ServerName subdomain.example.com
    Redirect permanent / https://subdomain.example.com/
</VirtualHost>

NameVirtualHost *:443
<VirtualHost *:443>
    ServerName www.example.com
    ServerAlias example.com

    SSLEngine on
    SSLCertificateFile /var/ssl/www.example.com.crt
    SSLCertificateKeyFile /var/ssl/www.example.com.key
    SSLCACertificateFile /var/ssl/intermediate.crt

    DocumentRoot /var/www/admin-interface/public

    <Location />
        RewriteEngine On

        ...
    </Location>
</VirtualHost>
<VirtualHost *:443>
    ServerName subdomain.example.com

    SSLProxyEngine On
    ProxyPass / https://192.168.2.12:443/
    ProxyPassReverse / https://192.168.2.12:443/

    SSLEngine on
    SSLCertificateFile /var/ssl/subdomain.example.com.crt
    SSLCertificateKeyFile /var/ssl/subdomain.example.com.key
    SSLCACertificateFile /var/ssl/intermediate.crt
</VirtualHost>

 

Jeremy Davis's picture

Thanks for posting your progress and your final working config. Apologies that I wasn't along sooner to help you out, but really glad you got it working. This will be useful for others I am sure!
digg_de's picture

Hi, i now upgrade to turnkey 14.0 with apache 2.4.10. Now I've got a new error:

Proxy Error

The proxy server could not handle the request GET /.
Reason: Error during SSL Handshake with remote server

What is the difference between the configuration of apache 2.2 to apache 2.4 that causes this error?
Can everybody help?

Thanks!

Jeremy Davis's picture

Apache2.4 (as found in v14.x) will only read config files that explicitly have the .conf file extension, so start there. I.e.:
mv /etc/etc/apache2/sites-available/default /apache2/sites-available/default.conf
For other changes have a look at the Apache upgrade docs.

Don't forget to restart Apache when you're done.

If you still have problems check the Apache log (tail /var/log/apache2/error.log) for clues on what might be causing the issue.

digg_de's picture

Hi Jeremy,

once again! Thanks for your fast response, really!

Yes, i rename it to default.conf. The error.log contains some hints:

[Sat Jul 02 06:53:53.573896 2016] [ssl:warn] [pid 3651] AH01909: 127.0.1.1:12322:0 server certificate does NOT include an ID which matches the server name
[Sat Jul 02 07:01:54.807560 2016] [proxy:error] [pid 4186] (502)Unknown error 502: AH01084: pass request body failed to 192.168.2.12:443 (192.168.2.12)
[Sat Jul 02 07:01:54.807621 2016] [proxy:error] [pid 4186] AH00898: Error during SSL Handshake with remote server returned by /
[Sat Jul 02 07:01:54.807627 2016] [proxy_http:error] [pid 4186] AH01097: pass request body failed to 192.168.2.12:443 (192.168.2.12)

The problem is the verification of the SSL certificate. The apache server don't trust my certificate? I order this from my provider (its not self signed), i dont know whats wrong with my SSL certificate?

A quick solution is to disable SSL verification by adding this lines in the SSLProxyEngine section:

SSLProxyVerify none
SSLProxyCheckPeerCN off
SSLProxyCheckPeerName off
SSLProxyCheckPeerExpire off

But I'am not sure if this a secure solution?

 

Jeremy Davis's picture

To be able to proxy the traffic, Apache needs to be able to process it. Because the traffic is encrypted, unless the reverse proxy has the private key it can't proxy the encrypted SSL traffic.

So the "proper" SSL connection needs to terminate at the front end reverse proxy (not the backend server). IMO so long as the backend server is not public internet available, then the easiest is to just use plain HTTP between the proxy and the backend (so long as no one can listen in, no need to encrypt it IMO).

OTOH if your backend is connected via some hostile network (i.e. not direct private communication) or you are concerned about the possibility of someone snooping (e.g. a wifi hotspot running on the same network) then you'll need to set up an additional SSL connection between your proxy and your backend.

There are different ways to skin that cat; but it is well summarised on InfoSec StackExchange here. Personally I'd go with his first suggestion...

digg_de's picture

Yes, you are right. The internat traffic don't have to be encrypted. And yes, except someone is snooping our internal network.

But with the solution above the transfer is still encrypted, only the verification of the certificate is disabled. So, it should be save.

I'm just looking for a pretty solution and want to understand why the ssl verification in the apache 2.4.xx failed, but not in the apache 2.2.xx. I will just look in more apache specific groups ... i dont found a hint in the release notes.

Thanks g.g.

Jeremy Davis's picture

I missed the point that you made that it was working and only broke on the update. Perhaps it's worth posting a question on one of the StackExchange sites (http://stackoverflow.com/ http://webmasters.stackexchange.com/) or somewhere else? Maybe you can get the attention of someone who is more of an Apache master than me?!

FWIW, as I think I posted earlier, under the hood TurnKey is Debian (v13.x = Debian Wheezy; v14.x = Debian Jessie).

digg_de's picture

Hi Jeremy,

thanks a lot for your help and discussion. I will ask in an other forum and post my final results here.

g.g.

 

Jeremy Davis's picture

My knowledge is pretty broad but not very deep in most areas. If you get a good answer it'd be great if you could post back, then we can all learn! :)
Wasif Shaikh's picture

DO you know what was the resolution?
digg_de's picture

I dont find a solution for the SSL verification of the proxys. I use SSL, but i disable the verification by these lines:

 SSLProxyVerify none
 SSLProxyCheckPeerCN off
 SSLProxyCheckPeerName off
 SSLProxyCheckPeerExpire off

It works. Another way is to use not encrypted traffic between the internal server, but i dont try it.

 

Post new comment