How to use nginx to proxy a subdirectory to a subdomain

It’s common to host a wordpress blog on a subdomain like https://blog.example.com on separate servers from the main site for various reasons.

For SEO purpose(Google thinks subdomain is a separate site), you may want to use https://example.com/blog for your blog but keeping the blog installation on original server. It’s simply to do this using a proxy server.

For example:

www.example.com/example.com is on server A.
blog.example.com is on server B.
We have a proxy server C.

Now, we need setup the proxy for main domain www.example.com on server C.

The nginx site conf will look like this:

# proxy subdirectory to subdomain
location /blog/ {
    proxy_pass https://blog.example.com;
    proxy_set_header Host blog.example.com;
    # strip /blog/ from the path
    rewrite /blog/(.*) /$1 break;
}

# proxy everything else to main domain server
location / {
    # pass everything to example.com server
    proxy_pass http://server_A_IP;
    proxy_set_header Host $host;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header X-Forwarded-Proto http;

}

Test conf and restart nginx

nginx -t && systemctl restart nginx

Next, change main domain A record to the proxy server. Once DNS is propagated, you will need to install the SSL for main domain so that you can use https://example.com/blog to go to your blog.

certbot --nginx -d example.com

The only problem is that the links are still using the subdomain address blog.example.com. You can simple add following two lines in wp-config.php file to replace all subdomain links to the proxy address “example.com/blog”

define('WP_HOME', 'https://example.com/blog');
define('WP-SITEURL', 'https://example.com/blog');

Now, when you go to https://example.com/blog, you will see what you have on https://blog.example.com
All the blog posts/pages will also be translated to the proxy address like it’s hosting on the same server as the main domain.

Fix wordpress missing a temporary folder error

When you try to upload an image in WordPress Media Library, you got “Missing a temporary folder” error.

First, try switching Media Library from grid view to list view. Grid view use PHP to crop the thumbnails to proper dimensions which can use more CPU/RAM and cause your site hit server resource limit.

Second, check whether you are using PHP-FPM or not. If yes, you may reached the PHP-FPM max_children setting. You can either raising it or disable PHP-FPM.

 

Fix cpanel http 504 gateway timeout error

You got http 504 gateway time out error in browser when visiting your wordpress site, and you see fcgi timeout error like follows in /usr/local/apache/logs/error_log

[proxy_fcgi:error] (70007)The timeout specified has expired: [client xxx.xxx.xxx.xxx:8959] AH01075: Error dispatching request to : (polling)

To fix this, you need to increase the TimeOut and ProxyTimeout in Apache Configuration file. It’s best to change this for an individual user than in global virtual host file.

Eg: the cpanel user id is “USERNAME”

You need to create file /etc/apache2/conf.d/userdata/ssl/2_4/USERNAME/php-fpm.conf, then add following two lines to overwrite the default settings.

TimeOut 600
ProxyTimeout 600

Include Multiple Server IPs in one SPF record

When you have one mail server, you can use the mail server IP in your spf record

client_domain.com. TXT "v=spf1 ip4:10.0.1.1 ~all"

When you have multiple mail servers or multiple IPs on one mail server, you have to do this

client_domain.com. TXT "v=spf1 ip4:10.0.1.1 ip4:10.0.1.2 ip4:10.0.1.3 ip4:10.0.1.4 ip4:10.0.1.5 ~all"

This is not convenient and cumbersome especially when you will adding more servers and migrate client from older server to new one.

To make it simple, you can create one spf record using a subdomain to include all mail server IPs.

client_domain.com. TXT "v=spf1 include:_spf.cpanelcares.com ~all"

To make above record work, you need to add the TXT record like follows to your domain first:

Main spf record which includes all mail servers:

_spf.cpanelcares.com TXT "v=spf1 include:_netblocks1.cpanelcares.com include:_netblocks2.cpanelcares.com ~all"

The _netblocks1 subdomain includes all shared server IPs:
_netblocks.cpanelcares.com TXT "v=spf1 ip4:10.0.1.0/24 ip4:10.0.2.0/24 ~all"

The _netblocks2 subdomain includes all VPS server IPs:
_netblocks2.cpanelcares.com TXT "v=spf1 ip4:65.61.209.0/24 ~all"

PS: Inspired by Google.com’s spf record.

google.com. 3599 IN TXT "v=spf1 include:_spf.google.com ~all"

_spf.google.com. 299 IN TXT "v=spf1 include:_netblocks.google.com include:_netblocks2.google.com include:_netblocks3.google.com ~all"

_netblocks.google.com. 3599 IN TXT "v=spf1 ip4:35.190.247.0/24 ip4:64.233.160.0/19 ip4:66.102.0.0/20 ip4:66.249.80.0/20 ip4:72.14.192.0/18 ip4:74.125.0.0/16 ip4:108.177.8.0/21 ip4:173.194.0.0/16 ip4:209.85.128.0/17 ip4:216.58.192.0/19 ip4:216.239.32.0/19 ~all"