Setup guide · ~5 minutes
How to reach any self-hosted app from anywhere
Self-hosting is the easy part. Getting to your server when you are not at home is where most people stall, because the usual answer is port forwarding plus dynamic DNS plus a reverse proxy plus certificates. This guide replaces that stack with one container, in about five minutes, and it works even if your ISP has you behind CGNAT.
What you need
- An app that serves HTTP. If you can open it in a browser on your LAN, it works here.
- One command's worth of access to a machine on that network. You never touch the router.
- Enough upload bandwidth if you are streaming video. 10 Mbps carries one 1080p stream, 4K wants about 35. Setup measures this for you.
Step 1: Create an account and pick a plan
Sign up, verify your email, pick a tier. You pay per server, not per app or per device, so one plan covers everything on that machine:
- Basic: 20 Mbps for $4/mo. Fits one 1080p stream.
- Plus: 50 Mbps for $8/mo. Fits 4k stream or 2–3 concurrent 1080p.
- Pro: 100 Mbps for $15/mo. Fits multi-user households, 4k remux.
Throughput is the cap on our end. If your home upload is 12 Mbps, the 100 Mbps plan buys you nothing. Start small; changing plans later is two clicks in the billing portal.
Step 2: Find your app's address and port
You need two things: the LAN IP of the machine running the app, and the port
it listens on. Together they look like 192.168.1.50:8096. Common defaults:
| App | Default port | |
|---|---|---|
| Jellyfin | 8096 | Media streaming |
| Plex | 32400 | Media streaming |
| Immich | 2283 | Photo library |
| Navidrome | 4533 | Music streaming |
| Audiobookshelf | 13378 | Audiobooks and podcasts |
| Home Assistant | 8123 | Home automation |
| Radarr | 7878 | Authentication off by default |
| Sonarr | 8989 | Authentication off by default |
Confirm against your own setup rather than trusting the table. Any of these can be remapped in a compose file, and plenty of people have. If you are unsure, the port is whatever you type into your browser at home.
Step 3: Run the agent
After checkout you land on a setup page with your registration token already filled into ready-to-paste commands. The Docker one looks like this:
docker rm -f tunnelo 2>/dev/null; docker run -d --name tunnelo --restart unless-stopped --cap-add NET_ADMIN --device /dev/net/tun -v tunnelo-agent:/var/lib/tunnelo-agent -e TUNNELO_TOKEN=YOUR-TOKEN -e TUNNELO_SERVICE_URL=http://192.168.1.50:8096 ghcr.io/abiteman/tunnelo-agent:latest
Point TUNNELO_SERVICE_URL at the LAN IP from step 2. Never localhost or 127.0.0.1: inside the agent's own container those mean
the container itself, not your server, and this is the single most common setup mistake. The
leading docker rm -f tunnelo 2>/dev/null; makes the command safe to re-run
after a typo. There is a curl | sh installer for bare metal and an Unraid template
in Community Apps.
Running more than one app? Swap TUNNELO_SERVICE_URL for TUNNELO_SERVICES=192.168.1.50:8096,2283,8123. Bare ports after the first reuse
that host. Each app gets its own https address on the same tunnel, and they share your plan's
throughput rather than multiplying it.
Already running WireGuard on a router (OpenWrt or pfSense) or a NAS? Or did docker run fail because the host has no /dev/net/tun? Use external
mode. The agent stays unprivileged and hands you a wg-quick config for whatever you already
run.
Step 4: Turn on authentication first
This step is easy to skip and expensive to skip. The moment the tunnel is up, that address is reachable by anyone who knows it. Media servers like Jellyfin and Plex force a login out of the box, so they are fine. Plenty of self-hosted tools do not: Radarr and Sonarr ship with authentication disabled, and several dashboards and *arr-adjacent utilities assume they will only ever be on a trusted LAN.
Open each app's settings and enable authentication before you expose it, not after. The tunnel gives your app a public address; it does not give it a login screen.
Step 5: Connect and use your address
The setup page updates on its own, usually inside a minute. When it flips to Connected you get your permanent address
(your-name.tunnelo.app) and an upload speed test result. Pay attention
to that number: it is the honest ceiling on streaming, and knowing it up front beats debugging
buffering complaints later.
Open the address in any browser, or enter it as the server URL in a native app. Everything passes through unchanged, including the parts that break on naive proxy setups: range requests for seeking, websockets for live updates, and large file transfers.
Troubleshooting & FAQ
Which apps work with this?
Anything that serves HTTP. The gateway maps a subdomain to an address and port on your tunnel and forwards traffic unchanged, so it never needs to know what is on the other end. Media servers are the common case and the proxy is tuned for them, but a dashboard, a wiki, a git server, or an internal tool all work the same way.
What does not work?
Anything that is not HTTP. Game servers, SSH, raw TCP or UDP services, and SMB shares are out of scope, because the gateway routes by hostname and there is no hostname in those protocols. If your app is reachable in a browser, it will work here.
Can I expose several apps at once?
Yes, and this is the normal setup. Set TUNNELO_SERVICES to a comma-separated list instead of a single TUNNELO_SERVICE_URL and each app gets its own https address on the same tunnel. There is no cap on how many. They share your plan throughput rather than multiplying it, because the ceiling is per server.
Do I need to open ports on my router?
No, and there is nothing useful you could open. Your server dials out to the gateway the same way a browser dials out to a website, so no inbound connection is ever required. That is what makes it work behind CGNAT, Starlink, 5G home internet, and ISP routers with no usable admin page.
How fast will it be?
Your home upload speed is almost always the real limit, not your plan. Figure roughly 10 Mbps of upload per 1080p video stream and about 35 for 4K. Anything that is not video barely registers. Setup runs a speed test so you see your actual number before you rely on it.
Is my traffic private?
It is encrypted the whole way: HTTPS from your device to the gateway, then WireGuard from the gateway to your server. We do not inspect what passes through and keep no record of what you opened or when.
What if I already run WireGuard?
Use external mode. The agent runs unprivileged and writes a wg-quick config you add to your existing setup, so your private key never leaves your machine. This is also the answer if docker run fails on /dev/net/tun, which happens on some restricted VMs and cloud hosts.
Do I pay per app or per device?
Neither. Pricing is per server. Every app behind that tunnel and every device that connects to it is included. Plans differ only in tunnel speed.
Guides for specific setups
- Jellyfin remote access, including what changes if you are moving over from Plex.
- OpenWrt and pfSense, if you would rather terminate the tunnel on your router than on the server.
Ready to try it?
One command and your server is reachable from anywhere, minus the router surgery. Every plan starts with a free trial.
Get your address