How to preview a site on a new server without editing the hosts file

本文为原文前 6,000 字符的节选翻译,完整内容请查看原文。

Every migration ends up in the same spot. The files are on the new server, the database is imported, and now you’ve got to work out whether it actually works before you point DNS at it and find out in public. The usual answer is to edit your hosts file. It’s a good answer. It’s also older than DNS itself, and it has limits that are easy to forget until they bite.

每一次迁移最终都会走到同一处。文件已上传至新服务器,数据库也已导入,现在你需要确认它是否真的能正常工作,然后再将 DNS 指向它,以免在公开环境下发现问题。通常的解决方法是编辑 hosts 文件。这是一个不错的方案,但它比 DNS 本身还要古老,且存在一些容易被忽视的局限性,直到它们造成麻烦时你才会想起。

What editing the hosts file actually does: Before your computer asks a DNS server where example.com lives, it checks a plain text file on disk. If that file has a line for the hostname, the lookup stops right there and nothing goes out over the network. You’ll find it here: Windows: C:\Windows\System32\drivers\etc\hosts; macOS and Linux: /etc/hosts. Both are protected system files. On Windows you need to run your editor as administrator, and on macOS or Linux you need sudo. It’s one mapping per line, with the IP address first: 203.0.113.42 example.com, 203.0.113.42 www.example.com.

编辑 hosts 文件实际上做了什么:在你的计算机询问 DNS 服务器 example.com 的位置之前,它会先检查磁盘上的一个纯文本文件。如果该文件包含对应主机名的行,查找过程就会立即停止,且不会有任何请求发送到网络上。你可以在以下位置找到它:Windows 系统为 C:\Windows\System32\drivers\etc\hosts;macOS 和 Linux 系统为 /etc/hosts。两者都是受保护的系统文件。在 Windows 上,你需要以管理员身份运行编辑器;在 macOS 或 Linux 上,则需要使用 sudo。每行对应一个映射,IP 地址在前,例如:203.0.113.42 example.com,203.0.113.42 www.example.com。

The reason this trick works at all comes down to what your browser sends. It still sends Host: example.com in the request, and the TLS handshake still carries example.com as the SNI value. So the new server sees the real domain name, picks the right virtual host and serves the right certificate, exactly as it would after a real DNS change. That’s why editing the hosts file beats typing the server’s IP address into the address bar. If you visit http://203.0.113.42 directly, the browser sends Host: 203.0.113.42, and the server has no idea which site you’re after. You get the default virtual host, which is usually an Apache welcome page, a 404, or someone else’s website on the same box. People see that and assume the migration failed. It didn’t. They just asked the wrong question. So the hosts file gets the technical part right. Its problems are all practical ones.

这个技巧之所以有效,归根结底在于浏览器的发送内容。它在请求中依然会发送 Host: example.com,且 TLS 握手过程也会携带 example.com 作为 SNI 值。因此,新服务器能看到真实的域名,选择正确的虚拟主机并提供正确的证书,这与真正的 DNS 变更后的效果完全一致。这就是为什么编辑 hosts 文件比直接在地址栏输入服务器 IP 地址更有效。如果你直接访问 http://203.0.113.42,浏览器会发送 Host: 203.0.113.42,而服务器根本不知道你想要访问哪个站点。你会得到默认的虚拟主机页面,通常是 Apache 欢迎页、404 错误,或者是同一台机器上其他人的网站。人们看到这些就会认为迁移失败了,其实不然,他们只是问错了问题。所以,hosts 文件在技术层面是正确的,但它的问题全在于实际应用中。

Where the hosts file runs out of road: It only works on the machine you edited. This is the biggest problem by far. A hosts entry is local. Your client can’t see what you see, your colleague can’t either, and there’s no way to email it to anyone. To bring even one other person along, you’d have to walk them through opening a protected system file with administrator rights on their own computer. On a managed work laptop that’s often blocked by policy, so no amount of patience on the call is going to get you there.

hosts 文件的局限性:它仅在你编辑的机器上生效。这是目前最大的问题。hosts 条目是本地的。你的客户看不到你所看到的,你的同事也看不到,而且无法通过电子邮件发送给任何人。要让哪怕另一个人参与测试,你都必须指导他们在自己的电脑上以管理员权限打开受保护的系统文件。在受管理的办公笔记本电脑上,这通常会被策略阻止,所以无论你在电话里多有耐心,也无法解决这个问题。

There are no wildcards: The hosts file matches exact hostnames, and there’s no syntax for *.example.com. If you’re migrating a WordPress multisite, or anything with blog., shop., app. and a few others, you need a line for every single one, and you need the full list before you start. Miss one and you get a confusing, half-broken result, where some of the site comes from the new server and some quietly comes from the old one.

没有通配符支持:hosts 文件匹配的是精确的主机名,且没有 *.example.com 的语法。如果你正在迁移 WordPress 多站点,或者任何带有 blog.、shop.、app. 等子域名的项目,你需要为每一个子域名添加一行,并且在开始前必须列出完整的清单。漏掉一个就会得到一个令人困惑的、半残的结果,即部分站点内容来自新服务器,而另一部分则悄悄地来自旧服务器。

Phones and tablets are out: There’s no supported way to edit the hosts file on a stock iPhone or Android device. Unless you root or jailbreak it, you simply can’t test on mobile this way. That hurts more than it sounds, because mobile is where layouts break, where buttons end up too close together, and where a slow new server is most obvious.

手机和平板电脑无法使用:在未修改的 iPhone 或 Android 设备上,没有受支持的方法来编辑 hosts 文件。除非你进行 Root 或越狱,否则根本无法通过这种方式在移动端进行测试。这比听起来更糟糕,因为移动端往往是布局容易崩溃、按钮间距过窄,以及新服务器响应缓慢最容易被察觉的地方。

Firefox may ignore it completely: Firefox enables DNS over HTTPS, which looks names up inside the browser over an encrypted connection to a DNS provider. When that’s on, the lookup never reaches your operating system, so your hosts file gets skipped entirely. Your entry can be correct and saved and still be completely ignored. Mozilla has been tracking support for local address overrides under DoH in bug 1453207 for years. Chrome behaves differently here and generally still honours the file, because it checks the system resolver for local entries. That’s why the same test can pass in one browser and fail in another on the same machine. If you’re relying on the hosts file, check whether DoH is switched on before you draw any conclusions about the server.

Firefox 可能会完全忽略它:Firefox 启用了 DNS over HTTPS (DoH),它通过加密连接在浏览器内部向 DNS 提供商查询域名。当此功能开启时,查询请求永远不会到达你的操作系统,因此你的 hosts 文件会被完全跳过。即使你的条目正确且已保存,它也可能被完全无视。Mozilla 多年来一直在 bug 1453207 中跟踪 DoH 下本地地址覆盖的支持问题。Chrome 在这方面的表现不同,通常仍会遵循该文件,因为它会检查系统解析器以获取本地条目。这就是为什么在同一台机器上,同一个测试在一个浏览器中可以通过,而在另一个浏览器中却会失败。如果你依赖 hosts 文件,在对服务器下结论之前,请先检查 DoH 是否已开启。

Caches will lie to you for a while: Editing the file doesn’t clear what your system already remembers: Windows: ipconfig /flushdns; macOS: sudo dscacheutil -flushcache then sudo killall -HUP mDNSResponder; Chrome, separately: visit chrome://net-internals/#dns and clear the host cache. Skip this and you can easily lose twenty minutes debugging a server that was fine all along. The commands for Linux, Firefox and phones are in how to flush DNS. You have to remember to take it out: A forgotten hosts entry makes for a really nasty bug. You finish the migration, DNS changes properly, everyone moves on, and your own machine keeps pointing at the old IP because the line never got removed. Weeks later the site looks frozen or broken, but only for you, and nobody else can reproduce it. It’s the kind of problem that can swallow a whole afternoon before anyone thinks to check.

缓存会欺骗你一段时间:编辑文件并不会清除系统已经记住的内容:Windows 使用 ipconfig /flushdns;macOS 使用 sudo dscacheutil -flushcache 然后 sudo killall -HUP mDNSResponder;Chrome 则需要单独访问 chrome://net-internals/#dns 并清除主机缓存。跳过这一步,你很容易浪费二十分钟去调试一台本来完全正常的服务器。Linux、Firefox 和手机的命令可以在“如何刷新 DNS”中找到。你必须记得将其删除:被遗忘的 hosts 条目会导致非常棘手的错误。你完成了迁移,DNS 也已正确更改,大家都在继续工作,而你自己的机器却因为那行代码没被删除,依然指向旧的 IP。几周后,网站看起来卡死或崩溃了,但只有你一个人遇到这种情况,其他人无法复现。这类问题可能会耗费整个下午的时间,直到有人想到去检查它。

How to preview a site on a new server without touching the hosts file: The alternative is to take the same trick off your machine and put it behind a URL. A preview link works as a reverse proxy. You give it your domain and the new server’s IP address, and it hands you back a link on a subdomain, something like x7k3p.dnspreviewer.com. When you open that link, the proxy connects to your new server and sends Host: example.com along with it, plus the matching SNI on the TLS connection. So the new server sees the same request it would after a real DNS change. You get the right virtual host and the right certificate behaviour, which is the whole point of the hosts file trick, only now it’s a link.

如何在不触碰 hosts 文件的情况下预览新服务器上的站点:另一种选择是将同样的技巧从你的机器上移出,并将其置于一个 URL 之后。预览链接的作用类似于反向代理。你提供域名和新服务器的 IP 地址,它会返回一个子域名链接,例如 x7k3p.dnspreviewer.com。当你打开该链接时,代理会连接到你的新服务器,并随之发送 Host: example.com,以及 TLS 连接上匹配的 SNI。因此,新服务器看到的请求与真正的 DNS 变更后的请求完全相同。你得到了正确的虚拟主机和正确的证书行为,这正是 hosts 文件技巧的核心目的,只不过现在它变成了一个链接。

That one change fixes most of the list above in one go. You can send a link to a client. It works on a phone without any setup. It doesn’t need administrator rights, it doesn’t matter whether someone’s using Firefox with DoH, and there’s nothing left behind on anyone’s machine to forget about. Wildcards stop being a problem too, because the proxy can cover a whole domain and all its subdomains, so you’re not listing them out by hand. DNS Previewer does this for free, wildcards included. You can also choose whether the connection to your serve…

这一改变一次性解决了上述列表中的大部分问题。你可以将链接发送给客户。它可以在手机上直接使用,无需任何设置。它不需要管理员权限,无论用户是否使用开启了 DoH 的 Firefox 都没有关系,而且不会在任何人的机器上留下需要清理的痕迹。通配符也不再是问题,因为代理可以覆盖整个域名及其所有子域名,所以你无需手动列出它们。DNS Previewer 可以免费实现这一点,包括通配符支持。你还可以选择连接到你的服务器时是否…