---
title: "The most secure inbound port is the one you never open"
date: 2026-06-23
summary: "Exposing self-hosted services to the internet with zero open ports, zero port-forwarding, and the origin's IP never leaving the building."
tags: ["cloudflare", "networking", "security", "zero-trust", "kubernetes"]
draft: false
hero: "/blog/outbound-only-exposure.webp"
heroAlt: "A smooth sealed dark monolith with no doors; a single thin thread of light arcs out from inside it to a distant glowing cloud-edge node."

---

The default way to put a home service on the internet is to forward a port: poke a hole in the router, map
it to the box, and hope the thing behind it never has a bad day. Every open port is a standing invitation
that's online whether or not anyone's knocking.

There's a better shape: don't open anything. Let the origin dial *out*.

![Outbound-only exposure - public traffic hits a Cloudflare edge with WAF and geo rules; the origin holds a single outbound tunnel; nothing is port-forwarded](/diagrams/outbound-exposure.svg?v=2)

## The tunnel dials out

A lightweight connector runs next to the service and opens a persistent **outbound** connection to the edge
network. Public traffic arrives at the edge, and the edge hands it back down that already-open tunnel. The
router has no inbound rule. The origin's public IP is never advertised. Port-scan the home connection and
there's nothing listening, because there isn't.

You've inverted the trust direction: instead of the internet reaching *in*, the box reaches *out*.

## Same name, two answers

The wrinkle is DNS. I run **split-horizon**: the internal domain resolves to in-cluster ingress for anyone
on the LAN, and the public domain resolves through the edge for the outside world. Same services, two names,
two answers depending on where you're standing, and the internal estate is never reachable through the
public path.

This bites in a non-obvious way too: a pod *inside* the cluster can't resolve the public hostname (it gets
the internal view), so any server-side callout has to target the internal service address directly.
Browser-facing stays public; machine-to-machine stays internal.

## The edge is the perimeter

Because every request now funnels through one edge before it ever touches home, that edge *is* the firewall.
So the controls live there, not on the origin:

- geo-fence to the regions you actually serve,
- rate-limit the authentication endpoints,
- put access control in front of anything administrative.

The origin's job shrinks to one thing: hold the tunnel open and serve. Everything hostile is filtered a
continent away.

## The safest port is the one never listening

Exposure isn't binary, and it isn't a synonym for port-forwarding. Push the perimeter out to an edge you
don't host, make the origin speak only outbound, and the attack surface at home collapses to zero open
ports. The safest port is the one that was never listening.
