Easy way to view a website at a different IP than associated with hostname?

1

Some background — WordPress is really annoying in terms of what hostname you access it from, which makes creating testing environments rather painful (That is, I could create a subdomain for staging, y.x.com, but then WordPress would set all the links in the database as being from there and not x.com, which is where they will be as soon as I do the DNS changeover). To get around this, I've setup an alias in my /etc/hosts file, so I don't have to keep changing the domain name in WP's settings.

In other words: right now I have a live site running on IP x and hostname x.com. I want to leave the live site running, and have setup a staging machine at IP y, accessed via the hostname x.com, using an entry in the aforementioned /etc/hosts.

My question: How do I show the staging machine to the client without having them edit their /etc/hosts file? Is there a service online that setups an iframe and shows you a particular IP as a particular hostname?

Thanks!

Edit: I'm not asking how to setup my DNS records; they're good for the moment. I can browse to the staging machine just by typing its IP into the address bar, and WordPress loads and everything's great, except all the links are to x.com, and clicking them takes me to the live/production site. I can rectify this by putting an entry into my local machine's hosts file (I.e., /etc/hosts), which overrides the public DNS records to the live site and instead shows me the staging machine. I'm essentially wanting a way to do this easily for my client, that is, without him having to edit his hosts file.

aendrew

Posted 2014-02-15T15:58:22.983

Reputation: 147

1Why you do not change the dns record? – Mehraban – 2014-02-15T16:16:59.920

@SAM Because there's an existing live site currently running and it will go offline if I change the DNS record. – aendrew – 2014-02-15T16:39:57.253

Related: Browser with its own hosts file?

– Arjan – 2014-03-16T08:19:24.063

Answers

1

Map x.com/staging to another server

Assuming you're running on Apache, proxying might do the trick. Running a Reverse Proxy in Apache suggests the following might work, but I did not test it:

ProxyPreserveHost on
ProxyPass /staging/ http://y.y.y.y/
ProxyHTMLURLMap http://y.y.y.y /staging

<Location /staging/>
    ProxyPassReverse /
    ProxyHTMLEnable On
    ProxyHTMLURLMap / /staging/
    # We need to peek into the HTML, so ensure we don't get gzip'd content:
    RequestHeader unset Accept-Encoding
</Location>

Above, a virtual folder /staging maps all from http://x.com/staging/ to / on the other IP address. To still keep using x.com as the host, I added ProxyPreserveHost.

All this will need the trailing slash; some standard rewriting could add that when needed:

# Add trailing slash if omitted
RewriteRule ^staging$ /staging/ [R=302,L]

Avoid sharing cookies: use a dedicated domain

However, to avoid very nasty problems with session cookies, I'd prefer a dedicated domain (preferably not even some subdomain of x.com). For that, remove all references to staging above. And to still send the expected domain name, I assume one could add an additional:

RequestHeader set Host x.com

When using such dedicated domain then Apache also won't have to rewrite any relative URLs, such as /some/page into /staging/some/page. However, this might imply you won't notice failures in rewriting absolute URLs (especially possible when JavaScript is involved). Like a failure to rewrite http://x.com/some/page back into http://client.mycompany.com/some/page might go unnoticed if the same URL exists on the production server, and the browser fetches that directly. That might be a benefit, or could be a disaster when you're still logged in to the production server and think you're changing content on the staging server...

Using .htaccess

Just for posterity, earlier I figured one could also use something like the following in a .htaccess file:

# Does NOT work (for me). On the target server, this gets me:
#   HTTP_HOST = y.y.y.y            - from the proxy request? Expected x.com
#   HTTP_X_FORWARDED_HOST = x.com  - from Host
#   HTTP_X_MY_DUMMY = x.com        - from X-My-Dummy, as expected

RewriteEngine On
RequestHeader set Host x.com 
RequestHeader set X-My-Dummy x.com
RewriteRule ^(.*) http://y.y.y.y/$1 [L,P] 
ProxyPassReverse / http://y.y.y.y/

However, ProxyPassReverse does not seem to be allowed in .htaccess. And some basic testing seems to reveal that the [P] proxy also always adds its own Host header, and translates my Host into X-Forwarded-Host. This could very well be related to the shared virtual hosting that I used for some quick test. But ProxyPreserveHost cannot be used in .htaccess.

See Apache's mod_proxy, mod_headers and mod_rewrite documentation.

Arjan

Posted 2014-02-15T15:58:22.983

Reputation: 29 084

I have this setup as a virtualhost and it seems not to be working — y.y.y.y is the staging machine's IP in both instances, right? Seems like a solid approach though; I've done something similar in the past with Nginx. – aendrew – 2014-02-15T17:11:26.677

Yup, @aendrew, y.y.y.y is that staging's IP address. Any error? (I can have a closer look tomorrow, 10 hours or more from now...) – Arjan – 2014-02-16T01:11:31.257

@aendrew, my testing failed too; see edited answer. – Arjan – 2014-02-16T15:24:28.583

And for Nginx, maybe these examples can help. Of course, Nginx might show the same issue with proxy_set_header as Apache's RequestHeader set, when trying to change Host.

– Arjan – 2014-02-16T16:07:27.063

Any luck, @aendrew? – Arjan – 2014-02-23T21:13:22.267

Apologies for the delay in getting back to you. This is a good and substantial answer, accepting for this question. – aendrew – 2014-04-26T18:32:09.007

1

you cannot bind a same hostname to different ip's Either you have to edit your DNS records to point the domain towards staging machine or you have to make local host resolution changes via hosts file.

Also you can add a check/condition variable via PHP or other language your site is running with, if present will open your website on staging machine for example http://examplesite.com/?staging=true

Saurabh Sharma

Posted 2014-02-15T15:58:22.983

Reputation: 848

While true, subdomains can have different IP addresses. (Just in case a reader doesn't know.) – Arjan – 2014-02-15T16:20:02.083

Ah yeah Subdomains can be an option too :) – Saurabh Sharma – 2014-02-15T16:22:35.290

Actually you can. That is often used to make a simple resilient service. Wouldn't help here as the first entry would always respond. – Julian Knight – 2014-02-15T16:41:15.390

@Arjan Yes, I could create a subdomain, y.x.com, but then WordPress would set all the links as being from there and not x.com, which is where they will be as soon as I do the DNS changeover. Alas, I can't do that until I get sign-off from the client, and they need to see it first.

I'm aware I can just setup WordPress at y.x.com and then use the WP_RELOCATE directive in wp-config.php, which will change all the links over, but then I have to do more DB work every time I push an updated dump. – aendrew – 2014-02-15T16:43:25.137

@SaurabhSharma The two sites are on different machines, I'd have to setup a bunch of Nginx proxy_pass directives to make that work properly, and at that point I might as well just put it on a subdomain as per Arjan's suggestion. I'm really just looking for a way to view a specific IP address, but send a specific Host header so that links work and whathaveyou. – aendrew – 2014-02-15T16:46:01.537

1

Another way is a normal proxy server (like Squid) and an edited /etc/hosts on the proxy server.

When you use a HTTP proxy, the browser of the client does no DNS lookup for x.com but connects to the proxy server and tells it to connect to x.com. Because you have bent x.com to another IP on the proxy server, you get the results from the staging server.

Ronny Lindner

Posted 2014-02-15T15:58:22.983

Reputation: 11

Seems like an interesting way to go — have any config tips? – aendrew – 2014-02-15T20:23:48.873

I'm just a user of this server myself - but you don't need anything special - you only need a base configuration (hardened so you don't provide an open proxy for everyone). You could combine the answer of Arjan and me - use the 2 lines with "proxy" in it (without rewrite or headers) and change the /etc/hosts file. – Ronny Lindner – 2014-02-15T20:51:10.340

If the proxy does the DNS lookup, then how does HTTPS work? (Newer extensions aside, the very first steps in SSL are only based on IP addresses, not on host names, right?) – Arjan – 2014-02-16T01:09:45.703

hmm, good question - I know that it definitely works for https and http with the proxy I'm using. Tomorrow I can look at the config and see if there is a trick to it. – Ronny Lindner – 2014-02-16T10:24:16.417

I looked at the squid.conf settings and there is no magic going on - it's a standard squid.conf with an ldap auth backend so it is no open proxy. For the https part - I have no idea how that works, but I get the certificate of the staging server and no certificate is configured on the proxy itself. – Ronny Lindner – 2014-02-17T18:10:57.683