Turning an Apache http site into secure https site via Nginx reverse proxy

Solution 1:

You can solve the problem in your option #1 (which, as you said, is a much better approach) by setting the HTTP_X_FORWARDED_PROTO in your nginx config with

proxy_set_header X-Forwarded-Proto $scheme;

and configuring WordPress to recognize it by appending this line to wp-config.php

if (isset($_SERVER['HTTP_X_FORWARDED_PROTO']) && $_SERVER['HTTP_X_FORWARDED_PROTO'] === 'https') {
    $_SERVER['HTTPS'] = 'on';
}

See also Wordpress support article for a variation of this solution.

Solution 2:

You should be able to tell Apache that the incoming request is being proxied from a HTTPS request with the proxy_set_header X-Forwarded-Proto "https"; declaration in the first setup

Solution 3:

Normally I would prefer to do all the heavy lifting on the reverse proxy and keep the backend site that gets exposed as original as possible.

Your problem seems to be in essence that the (WordPress) backend generates and uses (absolute) URI’s that differ from what you want visitors to use.

You can remedy that by rewriting the (HTML) content that WordPress generates in nginx with the ngx_http_sub_module. That will also allow you to rewrite absolute URL's with something similar to:

    location / {    
         sub_filter 'http://example.com/' 'https://www.example.com/' ;
         sub_filter 'http://www.example.com/' 'https://www.example.com/' ;
         sub_filter_once off;
         proxy_pass       http://Apache2-PHP5.6:80;
         proxy_set_header Host            $host;
         proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;                
    }