Asia/Shanghai
March 9, 2026

Multi-Home Self-Hosting: Secure Access from Anywhere

多家庭自托管:如何规划家庭局域网兼顾安全、便利与功能

Mingjian Shao
Multi-Home Self-Hosting: Secure Access from Anywhere
You have one home with all the servers, and four access scenarios with different constraints. Here's how to think about it — principles, not configs.
  • Home (main): This is where everything lives — NAS, hypervisor, Docker containers, the whole stack
  • Second home (family): Different city, different router, family members who just want things to work
  • Office: Behind a corporate firewall with deep packet inspection that detects and blocks VPN traffic
  • On the road: Hotel WiFi, mobile data, airport lounges — unpredictable networks
All the servers live in one place. All the users don't.Before getting into principles, here's what I'm working with and why.
Tailscale is the foundation. WireGuard-based mesh VPN. One command to set up on any device:
Bash
tailscale up --accept-routes --accept-dns
That's it. Your device is now on the mesh. The killer features:
  • Subnet routing: Run a Tailscale node as a gateway, and your entire home LAN becomes accessible to every device on the mesh. I run mine on a lightweight LXC container in Proxmox — always on, minimal resources.
  • --accept-dns: Tailscale pushes DNS config to connected devices. MagicDNS gives every node a hostname on your tailnet.
  • NAT traversal: Works through most firewalls and NATs via UDP hole punching. Falls back to relay servers (DERP) when direct connection isn't possible.
  • Zero config on the home side: No port forwarding, no dynamic DNS, no firewall rules. The subnet router advertises your LAN, and every Tailscale device can reach it.
The limitation: Tailscale is L3 only. It forwards IP packets — unicast only. That means no multicast, no broadcast, no mDNS. Your AirPlay speakers, AirPrint printers, and SMB shares won't be discovered over Tailscale. This is where ZeroTier comes in.ZeroTier operates at L2 — it creates a virtual Ethernet switch. Unlike Tailscale, it supports multicast and broadcast, which means mDNS works.I use ZeroTier specifically for local service discovery when I'm remote:
  • AirPlay to my living room speakers and Apple TV
  • AirPrint to the home printer
  • SMB file shares that rely on Bonjour/mDNS discovery
The setup: a ZeroTier node on the same LXC that runs Tailscale, configured as an L2 bridge with an avahi reflector that bounces mDNS packets between the ZeroTier virtual interface and the physical LAN.A word of warning: ZeroTier Central (the management dashboard) recently redesigned their UI, and the new version is missing critical features — you can't even access API token management from the new console. Use the legacy/classic dashboard if you need full control. Hopefully they fix this.CF Tunnel creates an outbound-only connection from your home to Cloudflare's edge. No ports opened on your router, no public IP needed. Traffic flows: user → Cloudflare edge → tunnel → your service.I use CF Tunnel for:
  • Admin interfaces I want to access from any browser without VPN (Unraid panel, NPM admin)
  • Content browsing where the 100MB upload limit and occasional latency don't matter
  • Backup access path when Tailscale is down or I'm on a device without it installed
What CF Tunnel is not good for:
  • Large file transfers — Cloudflare's free tier has a 100MB request body limit. Cloud storage / NAS file sharing won't work.
  • Latency-sensitive apps — traffic routes through Cloudflare's nearest PoP, which adds a hop.
  • Some apps that expect direct connections — password managers like Bitwarden can throw sync errors through the tunnel.
For those, I use NPM.NPM is a reverse proxy with a web UI. It handles domain-based routing: same IP, same port, different hostname → different backend service. All public-facing services go through NPM.In China, ISPs block ports 80 and 443 for residential connections. This is a regulatory thing — China Telecom, China Unicom, all of them. You physically cannot serve HTTPS on port 443 from your home IP. The workaround: pick a non-standard port (I use a high port), forward it through your router to NPM, and accept that all your URLs will have :port at the end.SSL certificates still work — you just can't use HTTP-01 validation (which needs port 80). Instead, use DNS-01 challenge: NPM talks to your DNS provider's API (Cloudflare, in my case) to prove domain ownership. No ports needed.When to use NPM vs CF Tunnel:
NPMCF Tunnel
Large files✅ No size limit❌ 100MB limit
Bitwarden✅ Works reliably❌ Sync errors
Zero-trust (no ports)❌ Needs port forward✅ Outbound only
Custom SSL✅ Full control✅ Automatic
Unraid runs all the services — media server, photo gallery, file manager, monitoring, everything. Docker containers on an internal bridge network, only exposed through NPM or direct LAN access.The Unraid web GUI itself runs on HTTPS with a self-signed certificate, which causes Chrome to silently disable disk caching. One of those things you discover after wondering why the GUI feels sluggish for months.PVE runs VMs and LXC containers. The Tailscale subnet router lives here as a tiny LXC (Debian, < 256MB RAM). The ZeroTier bridge also lives here. If the hypervisor is up, remote access works.For the second home: if you have enough devices that need to access your main home's services, don't install Tailscale on every device. Instead, run a Tailscale LXC or use a small router/mini-PC as a subnet router at the second location too. One node routes for the entire household.Not everything needs to be on the internet.Self-hosting guides love to start with "expose your services via reverse proxy with Let's Encrypt" — as if public access is the default. It shouldn't be.Split your services into tiers:
TierExamplesAccess
PublicPhoto gallery, file sharing, password vaultAnyone with URL + auth
VPN-onlyDashboards, monitoring, container managementTailscale/ZeroTier required
LAN-onlyRouter admin, hypervisor console, NAS managementPhysical/subnet only
The mental model: "if I lose my public IP tomorrow, which services must still work remotely?" Photos and files. Everything else can wait until I'm on VPN.All public services go through one reverse proxy on one port.The "why a port" part deserves explaining: Chinese ISPs block ports 80 and 443 on residential connections. Every home server admin in China hits this wall. You can't serve standard HTTPS. The workaround is a non-standard port — pick something above 1024, forward it through your router to NPM. Your URLs look like photos.example.com:XXXX instead of photos.example.com. Ugly, but functional.NPM handles domain-based routing:
  • photos.example.com:XXXX → photo gallery
  • files.example.com:XXXX → file manager
  • vault.example.com:XXXX → password vault
Same IP, same port, different hostname → different backend. The reverse proxy is the only thing touching the internet. Backends sit on an internal Docker network — they can't be reached directly even if someone knows your IP.Tier 1 (public): Photo gallery, file manager, password vault. Anyone with the URL and credentials can access them. These services have their own authentication. The exposure is intentional.Tier 2 (VPN-only): Monitoring, container management, system dashboards. No public exposure. Tailscale's subnet routing makes your entire home LAN accessible to VPN peers — every device thinks it's local.Tier 3 (LAN-only): Router admin, hypervisor console, NAS management panel. Subnet access only. Even Tailscale doesn't route to these unless the subnet router explicitly advertises them (and for some services, I don't).The key is intentionality. You decide what goes where based on who needs access and from where.Tailscale + subnet routing means your laptop at the office can access your NAS as if you were at home. No port forwarding, no DNS changes, no config on the home side.The corporate firewall problem: Some offices run DPI (deep packet inspection) firewalls that detect and block VPN protocols — including WireGuard, OpenVPN, and similar. If your office has one of these, Tailscale won't connect directly.Options:
  • Ask IT to whitelist it. Seriously. If your company allows personal devices and you have a reasonable relationship with IT, this is the least effort path. The firewall logs will show the connection attempt — it's better to get it approved than to fight the system.
  • SOCKS5 through a whitelisted port. If option 1 isn't possible, you can tunnel Tailscale through a SOCKS5 proxy on a port the firewall allows.
ZeroTier is useful here too — its protocol sometimes gets through firewalls that block WireGuard, though enterprise DPI can detect it as well. Don't rely on "stealth" — rely on policy.Family at the second home don't want domains, ports, or VPN apps. They want to tap an icon and see their show.The approach: install Tailscale on their key devices (phone, laptop, TV). One-time setup, runs in background. Then give them bookmarks to internal services by IP. No DNS, no HTTPS, no certificates to trust.If the second home has many devices (smart TVs, game consoles, IoT), don't install Tailscale on each one. Run a single Tailscale node (LXC, cheap mini-PC, or even a travel router) as a subnet router. One device routes for the whole household.The litmus test: "Can they access it without calling me?" If no → you've over-engineered.Today I tried to set up HTTPS for Homarr — an internal dashboard running on my Unraid NAS. The plan:
  • Local DNS override on the router (domain → NAS internal IP)
  • Real Let's Encrypt cert via DNS challenge (no port 80 needed)
  • NPM proxy with SSL — terminal curl confirmed it worked perfectly
  • Opened the browser... connection error
My browser's SOCKS proxy was intercepting all traffic, routing it through the internet instead of resolving locally. I could have fixed it — add the domain to the proxy bypass list, configure split DNS, tune Tailscale DNS settings...Or I could accept that HTTP on a trusted network is fine. The service is behind Tailscale. Nobody outside my VPN can reach it. Unencrypted HTTP on an encrypted WireGuard tunnel is already encrypted end-to-end.I spent an hour setting up HTTPS for a service that didn't need it. Classic over-engineering.Early on, I put all services behind NPM with public DNS records, then used NPM's Access Lists to restrict internal services by IP range. It "worked" but added attack surface for no benefit. If the service doesn't need public access, don't give it a public DNS record at all.
Four access paths, one home infrastructure. Each path has different constraints, different users, different needs.Don't start with "how do I expose everything?" Start with "who needs to access what, from where?"
  • Family at second home → Tailscale subnet router + direct IP bookmarks
  • You at office → Tailscale (whitelisted) + CF Tunnel as backup
  • You on the road → Tailscale for internal, NPM for public services
  • You at home → Direct LAN, zero overhead
Minimize exposure. One door for what must be public. Layer your trust. Carry your LAN. Don't make family call you.The goal isn't the most elegant architecture. It's things working without anyone calling you.
你有一个放满服务器的家,和四个不同限制的访问场景。这篇讲的是原则,不是配置教程。
  • 主家:所有基础设施都在这——NAS、虚拟化、Docker 容器,全套
  • 第二个家(家人):不同城市,不同路由器,家人只想东西能用
  • 办公室:企业防火墙做深度包检测,能识别并封锁 VPN 流量
  • 在路上:酒店 WiFi、手机热点、机场休息室——不可预测的网络环境
所有服务器在一个地方,所有人不在一个地方。先说我用了什么,为什么选它。
Tailscale 是基础。基于 WireGuard 的 Mesh VPN。任何设备一条命令就起来:
Bash
tailscale up --accept-routes --accept-dns
搞定。你的设备就在 mesh 上了。杀手级功能:
  • 子网路由(Subnet Routing):跑一个 Tailscale 节点当网关,整个家庭局域网对 mesh 上所有设备可见。我的跑在 PVE 的一个轻量 LXC 容器里——常驻运行,资源占用极低。
  • --accept-dns:Tailscale 推送 DNS 配置到连接设备。MagicDNS 给每个节点一个 tailnet 域名。
  • NAT 穿透:通过 UDP 打洞穿越大多数防火墙和 NAT。打不通就走 DERP 中继服务器。
  • 家里零配置:不用端口转发,不用 DDNS,不用改防火墙规则。子网路由器广播你的 LAN,所有 Tailscale 设备都能访问。
局限性:Tailscale 是纯 L3 的,只转发 IP 包——单播。这意味着 没有组播、没有广播、没有 mDNS。AirPlay 音箱、AirPrint 打印机、SMB 共享在 Tailscale 上发现不了。所以需要 ZeroTier。ZeroTier 工作在 L2——它创建一个虚拟以太网交换机。和 Tailscale 不同,它支持组播和广播,所以 mDNS 能用我用 ZeroTier 专门解决远程时的本地服务发现:
  • AirPlay 到客厅音箱和 Apple TV
  • AirPrint 到家里的打印机
  • 依赖 Bonjour/mDNS 发现的 SMB 文件共享
实现方式:在跑 Tailscale 的同一个 LXC 上也跑 ZeroTier,配置为 L2 桥接,加上 avahi reflector 在 ZeroTier 虚拟接口和物理 LAN 之间转发 mDNS 包。提醒一句:ZeroTier Central(管理后台)最近改版了新 UI,新版缺了很多关键功能——连 API Token 管理入口都找不到。如果需要完整控制,用旧版/经典后台。希望他们能修。CF Tunnel 从你家到 Cloudflare 边缘创建一个仅出站的连接。路由器不用开端口,不需要公网 IP。流量走向:用户 → Cloudflare 边缘 → 隧道 → 你的服务。我用 CF Tunnel 做:
  • 管理界面——不装 VPN 也能从任意浏览器访问(NAS 面板、NPM 后台)
  • 内容浏览——100MB 上传限制和偶尔的延迟无所谓的场景
  • 备用通道——Tailscale 挂了或者设备上没装的时候
CF Tunnel 不适合
  • 大文件传输——免费版有 100MB 请求体限制。网盘/NAS 文件共享用不了。
  • 延迟敏感的应用——流量绕 Cloudflare 最近的 PoP,多一跳。
  • 某些需要直连的应用——比如 Bitwarden 密码管理器通过隧道会报同步错误。
这些场景走 NPM。NPM 是带 Web UI 的反向代理。处理基于域名的路由:同一个 IP,同一个端口,不同域名 → 不同后端服务。所有公网服务都通过 NPM。国内运营商封了家庭宽带的 80 和 443 端口。电信、联通、移动都一样,这是监管要求。你从家庭 IP 物理上无法在 443 端口提供 HTTPS。解决方案:选一个非标准端口(1024 以上),路由器转发到 NPM,接受你所有的 URL 后面都带 :端口。丑,但管用。SSL 证书照样能签——只是不能用 HTTP-01 验证(需要 80 端口)。改用 DNS-01 challenge:NPM 通过 DNS 服务商的 API(我用 Cloudflare)证明域名所有权。不需要任何端口。NPM vs CF Tunnel 怎么选
NPMCF Tunnel
大文件✅ 无限制❌ 100MB 限制
Bitwarden✅ 稳定❌ 同步报错
零信任(不开端口)❌ 需要端口转发✅ 仅出站
自定义 SSL✅ 完全控制✅ 自动
Unraid 跑所有服务——媒体服务器、相册、文件管理、监控,所有东西。Docker 容器在内部桥接网络上,只通过 NPM 或局域网直连暴露。Unraid 自带的 Web GUI 用自签名证书跑 HTTPS,会导致 Chrome 默默禁用磁盘缓存。就是那种你纳闷了几个月"GUI 怎么这么卡"然后才发现的问题。PVE 跑虚拟机和 LXC 容器。Tailscale 子网路由器就在这里当一个轻量 LXC(Debian,不到 256MB 内存)。ZeroTier 桥接也在这里。只要虚拟化平台在线,远程访问就通。对于第二个家:如果有很多设备需要访问主家的服务,不要每个设备都装 Tailscale。在第二个家也跑一个 Tailscale LXC,或者用小路由器/迷你主机当子网路由器。一个节点路由整个家庭。不是所有服务都需要暴露到公网。自托管教程爱说"用反向代理配 Let's Encrypt 暴露服务"——好像公网访问是默认的。不应该是。把服务分层:
层级例子访问方式
公开相册、文件共享、密码库URL + 认证
仅 VPNDashboard、监控、容器管理Tailscale/ZeroTier
仅局域网路由器后台、虚拟化控制台、NAS 管理物理/子网访问
思维模型:"如果明天公网 IP 没了,哪些服务必须还能远程访问?"照片和文件。其他的等连上 VPN 再说。所有公开服务走一个反向代理,用一个端口。为什么需要非标准端口?国内运营商封了家庭宽带的 80 和 443 端口。电信联通移动都一样。你从家里的 IP 上根本开不了标准 HTTPS。解决方案:选个高位端口,路由器转发到反向代理,接受 URL 后面都带端口号。不好看,但能用。反向代理处理域名路由:
  • photos.example.com:XXXX → 相册
  • files.example.com:XXXX → 文件管理
  • vault.example.com:XXXX → 密码库
同一个 IP,同一个端口,不同域名 → 不同后端。反向代理是唯一接触公网的东西。后端在内部 Docker 网络上——就算知道你的 IP 也直接访问不了。第一层(公开):相册、文件管理、密码库。有 URL 和凭证就能访问。这些服务有自己的认证。暴露是故意的。第二层(仅 VPN):监控、容器管理、系统 Dashboard。不暴露公网。Tailscale 子网路由让所有 VPN 节点都以为自己在局域网上。第三层(仅局域网):路由器后台、虚拟化控制台、NAS 管理面板。只允许子网访问。即使 Tailscale 也不一定路由到这些服务——有些我故意不广播。关键是有意为之——根据谁需要从哪里访问,决定每个服务放哪一层。Tailscale + 子网路由 = 在办公室也能像在家里一样访问 NAS。不用端口转发,不用改 DNS,家里零配置。企业防火墙问题:有些公司跑 DPI(深度包检测)防火墙,能识别并封锁 WireGuard、OpenVPN 等 VPN 协议。如果你公司有这种 AC 设备,Tailscale 直连是连不上的。两个选择:
  • 找 IT 开白名单。 说真的。如果公司允许个人设备,而且你跟 IT 关系还行,这是最省力的路。防火墙日志会记录连接尝试——与其偷偷摸摸,不如光明正大报备。
  • SOCKS5 中转。 如果方案一走不通,可以通过一个防火墙放行的端口跑 SOCKS5 代理来隧道化 Tailscale 流量。
第二个家的家人不想管域名、端口、VPN 客户端。他们就想点一下图标看剧。做法:关键设备装 Tailscale(手机、笔记本、电视)。一次性设置,后台运行。然后给他们内网 IP 的书签。不用 DNS,不用 HTTPS,不用信任证书。如果第二个家设备很多(智能电视、游戏机、IoT),不要每个都装 Tailscale。跑一个 Tailscale 节点(LXC、便宜的迷你主机、或者旅行路由器)当子网路由器。一个设备路由整个家庭。检验标准:"他们能不能不打电话问我就访问成功?" 不能 → 过度设计了。今天我试着给 Homarr 配 HTTPS——一个跑在 Unraid 上的内部 Dashboard。计划是:
  • 路由器上配本地 DNS 覆盖(域名 → NAS 内网 IP)
  • 用 DNS Challenge 签了真正的 Let's Encrypt 证书(不需要开 80 端口)
  • NPM 反向代理加 SSL——终端 curl 完美通过
  • 打开浏览器……连接错误
浏览器的 SOCKS 代理截胡了所有流量,走了公网而不是本地解析。我本可以修——加绕过列表、配分流 DNS、调 Tailscale DNS 设置……或者接受:可信网络上 HTTP 就够了。服务在 Tailscale 后面,VPN 外面的人根本够不着。WireGuard 隧道上跑的未加密 HTTP,本身已经是端到端加密的。花了一个小时给一个不需要 HTTPS 的服务配 HTTPS。经典过度设计。Unraid 默认用自签名证书跑 HTTPS。Chrome 碰到不信任的证书会默默禁用磁盘缓存——所有 CSS、JS、图片每次都重新下载。Dashboard 上几十个 Docker 容器图标,每次导航都重新拉取,慢到怀疑人生。解决方案写在另一篇文章里——用 mkcert 生成本地信任的证书替换掉自签名的,Chrome 就恢复正常缓存了。早期我把所有服务都放 NPM 后面配了公网 DNS 记录,然后用 NPM 的 Access List 按 IP 段限制内部服务。"能用",但徒增攻击面。服务不需要公网访问,就根本别给它公网 DNS 记录。
四个访问路径,一套家庭基础设施。每条路径有不同的限制、不同的用户、不同的需求。别从"怎么把所有服务都暴露出去"开始。从**"谁需要从哪儿访问什么"**开始。
  • 家人在第二个家 → Tailscale 子网路由 + 直连 IP 书签
  • 你在办公室 → Tailscale(白名单)+ CF Tunnel 备份
  • 你在路上 → Tailscale 访问内部,NPM 访问公开服务
  • 你在家里 → 直连局域网,零开销
最小暴露。公开服务走一个入口。分层信任。随身带局域网。别让家人找你修电脑。目标不是搞个最优雅的架构。目标是东西能用,还不用老打电话问你。
Share this post:
Enjoy this post? Subscribe via RSS: English | 中文