Tailscale 组网实战:无公网 IP 把多台 VPS 连成私网,子网路由器、出口节点与 ACL

无公网 IP 的组网难题,Tailscale 怎么破

个人站长常遇到这样的场景:家里那台小主机想和云上 VPS 互相访问,但家宽没有公网 IP;几台分散在不同机房的服务器想组成一个内网互相通信,又不想折腾复杂的 VPN 配置和证书。传统的 OpenVPN、WireGuard 都能做,但密钥分发、NAT 穿透、动态 IP 跟踪这几件麻烦事都得自己扛。

Tailscale 的核心思路是「把 WireGuard 的加密能力 + 自动 NAT 穿透 + 身份管理」打包成一个开箱即用的网状网络(mesh)。你只要在各台机器上装好客户端、登录同一个账号,它们就自动互相可见,无需关心对方有没有公网 IP、IP 是否会变。它基于 WireGuard 协议,但把最难的组网部分自动化了。

本文讲清楚:Tailscale 的工作原理、安装与两台机器互通、子网路由器(subnet router)把整个内网接进来、出口节点(exit node)借道上网、ACL 做访问控制,以及几个新手容易踩的坑。它与 frp、Cloudflare Tunnel 的定位不同——后两者是「把单个服务映射出去」,Tailscale 是「把多台机器连成一个私网」,理解这个区别很重要。

Tailscale 的工作模型:控制面与数据面分离

理解 Tailscale 最关键的一点是:它分「控制面」和「数据面」两层,两者不是一回事。

  • 控制面(协调服务器 / coordination server):Tailscale 的官方服务器负责身份认证、交换各节点的公钥和可能的连接地址。它知道「谁是谁」,但不经过你的实际流量。
  • 数据面(节点之间的直连):真正的数据传输是两台机器之间的点对点 WireGuard 加密隧道,能直连就直连(NAT 打洞),打不通才走 Tailscale 的中继服务器(DERP)兜底。

这意味着:正常情况下你的数据不会经过 Tailscale 的服务器,端到端加密。但如果两点之间无法穿透 NAT,流量会经 DERP 中继——此时虽然仍是加密的,延迟和带宽会受中继影响。所以「能不能直连」直接影响体验,可以用 tailscale status 或 tailscale ping 查看当前是直连还是走中继。

每台机器会分到一个 100.x.y.z 的地址(Tailscale 的私有网段),这是一个虚拟的「内网 IP」,无论机器物理上在哪,都能用这个地址互相访问。密码学上每台机器有自己的节点密钥(node key),由控制面协助交换公钥后建立 WireGuard 会话。

第一步:安装与登录

官方提供了一键安装脚本,Debian/Ubuntu 上最省事:

curl -fsSL https://tailscale.com/install.sh | sh
systemctl enable --now tailscaled

然后把机器接入你的网络(Tailnet):

tailscale up

它会打印一个 URL,你在浏览器里打开、登录账号(Google/GitHub/邮箱等),这台机器就加入了。想加第二台机器,重复同样步骤、登录同一个账号即可。登录后查看状态:

tailscale status
tailscale ip -4

如果机器在无浏览器的服务器上,可以用 tailscale up --auth-key=xxxxx,其中 auth key 在管理后台(login.tailscale.com)里生成。生产环境自动部署强烈建议用带有效期的 auth key,而不是每次都手工点浏览器。

第二步:验证互通与直连状态

两台机器都上线后,用 100.x 地址互相 ping:

# 在 A 机器上
tailscale ping 100.x.x.x
# 输出里会标明是 "via DERP" 还是 "direct"

tailscale ping 用的是 ICMP over WireGuard,能明确告诉你链路类型。如果显示 via DERP(...),说明当前走中继,延迟可能偏高;如果反复几次后变成 direct,说明 NAT 打洞成功了。若长期只能走 DERP,可以检查两端是否都在对称型 NAT(如某些移动网络、双重 CGNAT)后面,这种情况打洞成功率低,考虑部署自己的 DERP 中继或接受中继。

实际验证连通性还是用普通工具更直观:

ping 100.x.x.x
ssh user@100.x.x.x
curl http://100.x.x.x:8080/health

第三步:用子网路由器把整个内网接进来

很多时候你不想在每台机器上都装 Tailscale,而是想让「一台网关机器」代表整个内网加入 Tailnet。这就是子网路由器(subnet router):在一台能访问目标内网的机器上开启 IP 转发,宣告你要暴露的网段:

# 1. 开启内核 IP 转发
echo 'net.ipv4.ip_forward = 1' | tee -a /etc/sysctl.d/99-tailscale.conf
echo 'net.ipv6.conf.all.forwarding = 1' | tee -a /etc/sysctl.d/99-tailscale.conf
sysctl -p /etc/sysctl.d/99-tailscale.conf

# 2. 在管理后台为这台机器的 key 启用 "Subnet routes" 权限,然后:
tailscale up --advertise-routes=192.168.1.0/24

之后需要到管理后台「Machines」页面,为这台机器 approve 这条路由(Tailscale 出于安全默认不会自动接受宣告的路由)。批准后,Tailnet 里的其他设备就能直接访问 192.168.1.0/24 网段里的设备了,无需在每台设备上装客户端。

子网路由器有个配套选项 --advertise-routes 必须配合后台 approve,很多人配完发现不通就是因为忘了批准。另外,子网路由器本身要能常在线,否则整个网段就断了。

第四步:出口节点——让流量借道某台机器出去

出口节点(exit node)是另一个方向的功能:让某台设备的全部上网流量都从指定的 Tailscale 节点出去。典型用途是在公共 WiFi 下加密上网、或者让访问某地的流量从某个地理位置的机器出去。

# 在作为出口节点的机器上
tailscale up --advertise-exit-node

# 在客户端上使用它作为出口
tailscale up --exit-node=100.x.x.x
# 查看/取消
tailscale up --exit-node=

同样,出口节点也要在后台 approve。注意出口节点会承载使用方的全部流量,对它的带宽和稳定性要求较高,个人用一般选一台带宽充裕的 VPS。出口节点和子网路由器是两种不同粒度:出口节点管「所有流量都从这走」,子网路由管「访问某个内网段从这走」,别搞混。

第五步:ACL 访问控制——私网也要讲权限

默认情况下,Tailnet 内所有设备之间可以互相访问。但生产环境你应该按「默认拒绝、显式放行」来配 ACL,避免任何一台被攻陷的机器横向访问整个网络。ACL 是一份 JSON 策略,在管理后台编辑:

{
  "acls": [
    { "action": "accept",
      "src": ["group:admin"],
      "dst": ["*:*"] },
    { "action": "accept",
      "src": ["tag:web"],
      "dst": ["tag:db:3306"] }
  ],
  "tagOwners": {
    "tag:web": ["group:admin"],
    "tag:db":  ["group:admin"]
  }
}

上面这份策略的含义:管理员组可以访问一切;被打了 tag:web 标签的 Web 服务器只能访问 tag:db 的 3306 端口,不能访问别的。标签(tag)通过 tailscale up --advertise-tags=tag:web 给机器打上。这样即使某台 Web 服务器被入侵,攻击者也碰不到数据库之外的东西。

ACL 还支持 SSH 规则,可以用 Tailscale 自己的 SSH 功能替代散落的密钥管理(tailscale up --ssh),按 ACL 里的 ssh 段决定谁能登录谁,审计也集中。这对多机器团队很方便。

第六步:常见坑与注意事项

  • 忘记后台 approve 路由/出口节点:这是最高频的「配了不通」原因,子网路由和出口节点都需要在管理页批准。
  • 以为流量一定不经过第三方:直连时确实不经过,但 NAT 打洞失败时会走 DERP 中继。对隐私敏感可自建 DERP。
  • 把 Tailscale 当公网映射用:它给的是私网地址(100.x 段),公网默认访问不到。要让外部访问服务,得配合 Funnel 或在网关做转发,别指望它能直接替代公网 IP。
  • 忽略 MagicDNS:开启 MagicDNS 后可以用机器名而非 IP 互相访问,非常方便,建议在后台打开。
  • 密钥管理:节点密钥过期或设备被移除后要重新登录。用 auth key 自动部署时设置合理的过期时间和 tag,别用永久 key 满地跑。
  • 性能预期:WireGuard 很轻量,但打洞失败走中继时带宽受中继限制。跨境链路尤其明显,必要时选直连或自建中继。

第七步:一个典型的个人站组网方案

把上面的能力组合起来,一个实用方案是:

  • 云上 VPS 装 Tailscale,作为主力节点,同时 --advertise-exit-node 兼作出口节点;
  • 家里的 NAS/小主机装 Tailscale,--advertise-routes=192.168.1.0/24 把家庭内网接进来;
  • 笔记本和手机装客户端,需要访问家里设备时直接连 100.x 地址或走 MagicDNS;
  • 用 ACL 把设备分组,Web 只能访问数据库端口,管理员才全通;
  • 用 tailscale status 定期确认链路是直连,必要时优化网络或部署中继。

这样一来,无论你人在哪,笔记本连上网络就能像在家一样访问各台机器,而且全部流量端到端加密,比暴露 SSH 到公网安全得多——因为你根本不需要开放任何公网端口。

小结

Tailscale 把 WireGuard 最难的部分——密钥分发、NAT 穿透、动态寻址——自动化了,让个人站长用极低成本搭出一张跨机房、跨家宽的私有网络。它和 frp、Cloudflare Tunnel 不是替代关系:那两者解决「把单个服务映射到公网」,Tailscale 解决「把多台机器连成一个私网」,实际部署中经常是配合使用。

上手路径建议:先在两台机器上装好、登录、确认直连互通,再根据需要引入子网路由器和出口节点,最后补上 ACL 收一收权限。记住两条铁律:路由和出口节点必须在后台 approve;Tailnet 不是公网,别指望它直接对外提供服务。守住这两点,你就拥有了一张既安全又省心的私网。

Last modification:October 3rd, 2026 at 09:24 pm

Leave a Comment