Domain mapping with WordPress multisite without using IP addresses

I am currently the lead back-end developer over at Highrise Digital, in charge of a large (over 500 sites) multisite installation of WordPress. Each site in the install has its own custom mapped domain, rather than using a subdomain of the primary site. In this post, I discuss how I set up domain mapping to websites in the WordPress multisite install, without pointing the domains to the servers IP address.

Background and setup

So let us step back a little bit and look a bit more at the setup of the installation. We have a long-term client who has lots of websites that are very similar. They have the same set of themes and plugins and we built them a website to deliver this using WordPress multisite.

I won’t go into the technicalities of the multisite build here for 2 reasons. The first being that I am not allowed to (NDA) and the second is that is is not massively important for this post.

What is important is that when our client wants to create a new site, for one of their clients, they simply add a new site in the WordPress multisite installation. At this point, this site is given a subdomain address. Let’s assume that the whole WordPress installation is at domain.com, a new site would get a URL of newsite.domain.com.

Obviously, clients don’t really want this as their site URL, they want to use their own domain. For that, we use domain mapping.

Mapping domains to a WordPress multisite installation

This assumes that the domain you are mapping is not currently in use.

When we first set up the site, WordPress didn’t (or so we thought at the time) support domain mapping out of the box, therefore we used the WordPress MU Domain Mapping plugin.

For the sake of this article though, I am going to talk through this without using the domain mapping plugin as WordPress support domain mapping without a plugin.

Step 1 – Change the domain DNS

In order for the site to use the domain, the domain must be pointed to the server where your WordPress multisite installation resides. There are a number of ways to do this:

  1. Change the nameservers of your domain, to the nameservers of your server. Most hosting companies will provide you of these when you create your account.
  2. Set the A record for domain.com and www.domain.com to point to the IP address of the server where the multisite installation resides
  3. Use a flattened CNAME record in order to avoid using IP addresses (see below)

Once the DNS starts to propagate the site will now resolve to the server where you have your WordPress multisite installed. At this point, of course, WordPress is not aware of this domain and neither is your server.

Step 2 – Create a new add-on domain

Different hosts do this differently, but if like me your host is using cPanel you need to navigate to add-on domains and add a new add-on domain for the domain you want to use. What is important here is that the add-on domains document root is set to point at the folder where your WordPress multisite is installed – likely htdocs or  public_html.

What happens then is that the server forwards the requests for that domain onto WordPress and WordPress should deliver you the correct site.

Step 3 – Add your site to WordPress multisite

To add a site click on My Sites > Sites > Add new and complete the details.

Once you have added your site, click on the My Sites > Sites menu item to see a listing of all your sites within your network.

edit-site-in-wpmu
Edit the site in order to change it URL or domain

On this listing when you hover over one of the rows, you will see an Edit link. Click this to edit the details of a site. You are then presented with a screen where you can set the address of this site. All you need to do is enter the address of the site in here, using https if you want the site to run over SSL (see below).

edit-site-address-wpmu

Domain mapping using a CNAME without the need for using an IP address

Mapping the domain with methods 1 (changing the domain nameservers) and 2 (pointing the A record to the server IP address) both have their problems.

If you choose to use the nameserver option it means that the server where the WordPress multisite resides is now in charge of all the DNS records for that domain. This means the domain owner no longer has control of those DNS records for adding things like MX and TXT records for example, often needed when setting up email solutions. They would have to ask you to add them each time which could become a pain.

If you choose the method of using the A record, this ties the domain mapping down to a specific IP address. What if the server you are using has issues and you need to move servers? That would have a different IP address and then the domain mapping would break. Also if you wanted to upgrade your server as your multisite instance grows, again the IP may change and that would break things.

Therefore I went about trying to find a solution to this problem and came across one that works really well, and is free!

Using a CNAME instead

Instead of pointing the domain name using A records you can point it using a CNAME record.

Let us assume that your WordPress multisite install resides at domain.com, what you would need to do in this instance is create a DNS A record entry which points to your sites IP address like so:

A    sites.highrise.network    10.11.12.13

Now you can point the domain you want to map (let us assume it is mymappeddomain.com) using a CNAME to that domain name like so:

CNAME      www.mymappeddomain.com   sites.highrise.network

In the above CNAME record note the www in front. This is because you cannot create a CNAME record for the naked domain – that is mymappeddomain.com. Therefore if the client wants both mymappeddomain.com and www.mymappeddomain.com to resolve to their WordPress site, this won’t work.

Therefore we need a way to allow a CNAME (which of course is an alias and points to another domain name) to the top level or naked domain name – is this case mymappeddomain.com

A Flattened CNAME record to the rescue

So I went on the hunt and asked around for whether anyone has solved this problem. This is when I came across the term flattened CNAME on the Cloudflare website.

They allow exactly this – the naked domain can be pointed to another domain, like an alias rather than an IP address. Therefore in Cloudflare we would set this up like this.

Using a naked domain as a CNAME in Cloudflare

Now because your domain points to (in this case) sites.highrise.network, we can always change the IP address of that A record to point to another one and the mapped domain will always reside to the correct place.

A note about SSLs with Let’s Encrypt

If you want to add an SSL certificate (and I urge you too) via the free Let’s Encrypt service, this will only work if your domain resolves to the server IP address which requests the certificate.

This won’t happen unless, in the image above, the two orange clouds are clicked and turned grey. I am not entirely sure what this is doing, but making them grey allows the SSL to be installed. Once installed you can turn them orange again.

You will also notice that Cloudflare offers SSL and caching etc. However I only want it for the DNS, and the great news is, is that the free plan they offer gives us all we need. To just use DNS, make sure you click on the Pause option on the Cloudflare dashboard home screen. This ensures that you only use DNS.

In our multisite scenario, this means that the client who owns the domain can signup for a free Cloudflare account, make these changes and everything should work. It also means they keep control of their DNS so they can add other records as and when they need to.

An added bonus is that the client can even add you as a user to their Cloudflare account so that you can make changes on their behalf!

5 responses

  1. Ross Wintle Avatar
    Ross Wintle

    Nice write-up, really helpful!

    Regarding the Lets Encrypt and the grey/orange icons:

    CloudFlare, by default, puts a “proxy” (actually a “reverse proxy”, for reasons I won’t go into) in front of your site. So when you put your site on CloudFlare, it puts CloudFlare between the visitor and your server. So instead of going:

    Visitor -> Server

    It goes

    Visitor -> CloudFlare Proxy -> Server

    If CloudFlare is working as a proxy you get the orange icon. When CloudFlare is not working as the proxy you get the grey icon showing the arrow skipping around the CloudFlare cloud. (Though, I just checked, and a site that is “paused” seems to have orange icons, even though CloudFlare isn’t doing anything. Which is confusing)

    When CloudFlare is working, it sets the DNS for the website URLs (usually the bare domain and www.) to point to CloudFlare’s proxy. This has a number of problems.

    1) If you want to SSH or FTP to the site, when you connect to the site you’ll actually be attempting to connect to CloudFlare’s proxy server. This is why many CloudFlare sites will have a “dev.” or “ftp.” subdomain that isn’t proxied. This allowed you to go direct to the server, skipping the proxy.
    2) When you’re setting up Let’sEncrypt you’re attempting to put a certificate on your web server. You will NOT put the Let’sEncrypt certificate on the CloudFlare proxy. When this is being set up, your server says to LE: “Can I have a certificate please”. LE runs some tests and is expecting to see your server when it connects to your website, and when it connects to your website what it actually sees is CloudFlare’s proxy. So because LE sees a different server to the one that is requesting the certificate, it looks like this is an invalid request and it bails. This is why CloudFlare and LE don’t work together if you’re using CF as a proxy. As you’ve noted, if you ONLY use CF for DNS then LetsEncrypt should work.

    There is actually another means of doing LetsEncrypt verification that, I think, uses DNS records. I’m not sure if cPanel and/or CloudFlare supports this or not.

    I probably got some technicalities wrong in there, but this should help understand the LetsEncrypt issue and the CloudFlare statuses.

    1. Thanks for that information Ross, makes a lot more sense. In this case I only want to use Cloudflare for DNS, to allow me to set the naked domain to point to another domain like a CNAME. Therefore I think the best option is to pause Cloudflare and turn the “clouds” grey, therefore, to not have Cloudflare sitting in the middle.

  2. […] Domain mapping with WordPress multisite without using IP addresses […]

  3. Hi Mark, I know that this blog entry was made in 2018 prior to the built in domain mapping in WordPress.

    1. Will the procedure above change?

    2. Just to clarify, when you indicate “create” the A Record in your example:

    A sites.highrise.network 10.11.12.13

    Is this A record added to mymappeddomain.com? If so, the underlying A Record on mymappeddomain.com is actually:

    sites.highrise.network.mymappeddomain.com???

    I appreciate your help.

    1. Mark Wilkinson Avatar
      Mark Wilkinson

      The A record in this example is creating a record for which to point mapped domains towards.

      The A record domain doesn’t have to be an actual domain in your multisite. I use `sites.domain.com` because it is something which makes sense when mapping domains to it.

Leave a Reply

Your email address will not be published. Required fields are marked *