Skip to content

nginx front

In LAN mode (and on any edge that keeps its listeners on loopback) nginx owns the external ports and proxies to the edge. One subcommand sets the whole thing up:

sh
sudo burrowee edge nginx --home "$HOME/.burrowee/edge"

Apply is the default. The command, in order:

  1. ensures the LAN certificate exists (generating a 10-year self-signed cert at ~/.burrowee/edge/lan-cert/ if absent),
  2. preflights the external ports (see below) — a conflict fails here, before anything is written,
  3. writes the stream snippet into the nginx conf dir,
  4. wires the include line into nginx.conf,
  5. persists lan_advertise_port and lan_cert into ~/.burrowee/edge/config,
  6. verifies with nginx -T that the snippet is actually loaded, runs nginx -t, and reloads nginx — or starts it if no master is running.

On success it prints the LAN certificate fingerprint:

LAN cert fingerprint: <sha256>
pin distributed via the next endpoint report

Gateways pick the pin up automatically; nothing to distribute by hand.

Why --home?

Apply writes into the nginx conf dir, so it usually runs under sudo — and sudo replaces $HOME with root's. --home points the command back at the service user's ~/.burrowee/edge so it reads the right config and certificate.

Flags

FlagDefaultMeaning
--home <dir>~/.burrowee/edgeThe edge component dir (required under sudo).
--listen-tls <port>443External TLS port nginx listens on (the :443 passthrough block).
--listen-lan <port>8448External LAN TLS port nginx listens on, proxying to the edge's lan_listen address.
--conf-dir <dir>/etc/nginx (Linux), /opt/homebrew/etc/nginx (macOS)The nginx configuration root.
--printPreview the rendered config on stdout. No writes, no certificate generation — the preview is byte-identical to what apply would install.
--rotate-lan-certMint a new LAN certificate, then apply. See below.

(--write and --reload are accepted from older instructions but do nothing — apply is the default.)

What gets written

The snippet lands at:

<conf-dir>/servers-stream/burrowee-edge-stream.conf

It contains plain server { listen …; proxy_pass …; } stream blocks: the LAN block (:8448 with ssl and the LAN cert, proxying to 127.0.0.1:9448) and — when the edge config has a TLS listener (tls_listen not off) — a :443 raw TCP passthrough to the edge's TLS port. The passthrough never terminates TLS: for that path TLS still ends inside the edge, with the console-pushed certificates, so nginx never sees plaintext.

To make nginx load the folder, the command idempotently ensures this in nginx.conf, at the top level (outside http {}):

nginx
stream {
    include servers-stream/*.conf;
}

If nginx.conf already has a top-level stream {} block, only the include servers-stream/*.conf; line is injected into it. The post-apply nginx -T check catches the unusual layouts: if the snippet still isn't loaded, the command prints the block to add by hand and exits with an error rather than leaving you half-configured. (The classic trap: many distros include conf.d/*.conf from inside http {}, where a stream {} block is silently dead — the include must sit at the top level. Also confirm nginx -V lists --with-stream.)

Port preflight

Before writing anything, the command probes each external port (--listen-tls, --listen-lan). A port already held by nginx serving this same snippet is fine — re-applying is idempotent. A port held by anything else fails fast, naming the holder and the right flag:

✗ port 8448 is already in use by another process (held by caddy pid 1234).
  Pick a different port and re-run, e.g.:
    burrowee-edge nginx --listen-lan <nginx-port>
  (and set lan_listen=127.0.0.1:<edge-port> + lan_advertise_port=<nginx-port> in ~/.burrowee/edge/config)

Because the preflight runs first, a conflict never leaves a broken snippet on disk. Pick a free pair — one external port for nginx, one loopback port for the edge — adjust the config keys as the message says, and re-run.

Rotating the LAN certificate

sh
sudo burrowee edge nginx --home "$HOME/.burrowee/edge" --rotate-lan-cert

This mints a fresh 10-year certificate and re-applies. Treat it as a deliberate operator act, because clients pin the fingerprint:

  • Gateways heal automatically — the new pin goes out in the edge's next endpoint report.
  • CLI clients do not. A CLI gets the pin inside the relay blob it pasted, and there is no push channel to update it — every CLI using this edge needs its relay blob re-pasted after a rotation. The command reminds you:
new fingerprint <sha256> — re-paste cli relay blobs (clis have no push channel)

Don't rotate casually. Rotate when the key may be compromised or the cert's host context changed — not as routine hygiene; the cert is good for 10 years.

QUIC is not fronted

If you enable a QUIC listener (quic_addr in the config), it is UDP — this TCP front does not carry it. The edge binds it directly; the command prints a note to that effect.