Opening ports to reach your own server is the usual advice, and the usual mistake. Every exposed port is something to patch, monitor, and eventually explain. Tailscale takes a different route: devices join a private mesh network over WireGuard, and nothing on the server needs a public listener.

Ringkasan singkat
- No inbound ports: devices join a WireGuard mesh.
- Approve subnet routes in the admin console.
- Restrict with ACLs; tag servers, not users.
tailscale servepublishes a local port privately.
This guide sets up Tailscale on an Ubuntu VPS, adds a second device, and exposes a home LAN without port forwarding.
Prerequisites
- Ubuntu 22.04 or 24.04 with
sudo. - A Tailscale account (free tier covers personal use).
- SSH access to the server you are configuring.
1. Understand what changes
Tailscale assigns each device an address in the 100.64.0.0/10 range and keeps a direct, encrypted connection between peers. Coordination happens through Tailscale's control plane; traffic itself goes peer to peer when possible.
Because of that, you do not need to open port 22, 8006, or 3000 to the internet. You open the service to your tailnet instead.
2. Install on the VPS
curl -fsSL https://tailscale.com/install.sh | sh
sudo tailscale up
The command prints a URL. Open it, authenticate, and the machine joins your tailnet. Verify:
tailscale status
tailscale ip -4
3. Add your laptop or phone
Install the client from Tailscale's download page, sign in with the same account, and confirm both devices appear in tailscale status. Then reach the server by its tailnet address or MagicDNS name:
ssh user@vps
ssh user@100.x.y.z
MagicDNS is what makes ssh user@vps work without editing /etc/hosts. It is enabled by default in most new tailnets.
4. Expose a home LAN
A subnet router lets the tailnet reach devices that cannot run Tailscale. On the machine inside your home network:
echo 'net.ipv4.ip_forward=1' | sudo tee /etc/sysctl.d/99-tailscale.conf
sudo sysctl -p /etc/sysctl.d/99-tailscale.conf
sudo tailscale up --advertise-routes=192.168.1.0/24
Then approve the route in the admin console: Machines → your host → Edit route settings. On the client side, accept routes:
sudo tailscale up --accept-routes
Without approval, the route stays advertised but unused — the most common reason a subnet router "does not work".
5. Restrict who can reach what
By default every device in a tailnet can reach every other device. For a server holding backups or admin panels, that is too broad. Tailscale ACLs are written in the admin console and look like this:
{
"acls": [
{ "action": "accept", "src": ["autogroup:member"], "dst": ["tag:server:22"] }
]
}
Tag the VPS, then grant only SSH. Everything else stays unreachable until you add a rule.
6. Serve a web UI without exposing it
sudo tailscale serve --bg 3000
This publishes the local port 3000 at an HTTPS address inside your tailnet, with a certificate managed by Tailscale. No DNS setup, no open port, no reverse proxy.
7. Exit node (optional)
To route general internet traffic through the VPS while travelling:
sudo tailscale up --advertise-exit-node
Approve it in the admin console, then enable it on the client. Expect the VPS bandwidth to become the limit.
8. Servers without a public IP
A machine behind CGNAT or a strict firewall still joins the tailnet: outbound connections are enough. Peers reach each other directly when possible and fall back to an encrypted relay through Tailscale's DERP servers when they cannot. The trade-off is latency, which you can measure with tailscale ping:
tailscale ping vps
If the output shows via DERP, traffic is relayed. Allowing UDP 41641 usually restores a direct path.
9. Key expiry and device hygiene
Device keys expire after 180 days by default. For a server you rarely touch, that means a silent disconnection months later. Open the machine in the admin console and choose Disable key expiry for infrastructure, while leaving it enabled for laptops and phones.
Remove devices you no longer use. A stale key is still a valid key until it expires, and the ACL cannot help if the device itself is trusted.
10. Tailscale SSH (optional)
Instead of managing authorized_keys, let the tailnet handle SSH authentication:
sudo tailscale up --ssh
Access is then governed by ACL rules, and every session is logged by identity rather than by key. Test it in a second terminal before disabling password logins, or you can lock yourself out of the only route in.
Troubleshooting
| Symptom | Cause | Fix |
|---|---|---|
| Devices listed but unreachable | Firewall blocking the tailnet interface | sudo ufw allow in on tailscale0 |
| Subnet route missing | Route not approved | Approve under Machine → Route settings |
| SSH works, web UI does not | Service bound to 127.0.0.1 | Bind to the tailnet IP or use tailscale serve |
| Slow transfers | Relay instead of direct connection | Check tailscale netcheck, allow UDP 41641 |
| MagicDNS name unresolved | DNS override on the client | Enable "Override local DNS" in DNS settings |
FAQ
Is this a VPN?
Yes, a mesh VPN built on WireGuard. Unlike a classic VPN, there is no central exit point unless you configure one.
Does traffic pass through Tailscale's servers?
Only for coordination and, when a direct path is impossible, as an encrypted relay. Enable tailnet lock if you care about control-plane trust.
Can I keep using UFW?
Yes. Allowing tailscale0 keeps the rest of the rules intact.
Free tier limits?
The free plan covers a small number of users and devices, enough for personal infrastructure.
Related guides:
0 comments:
Post a Comment