Proposal
Add a skill that teaches firstmate how to serve lavish - and other loopback-bound local servers spawned on the box - over Tailscale, so they are reachable from the captain's Mac/phone without exposing anything to the public internet.
Why
Lavish (and similar tools) bind to loopback only, so their session URLs are not reachable from another device. A naive reverse proxy also fails because lavish enforces a host allowlist and returns 403 forbidden host for an unrecognized Host header. The skill should encode the working recipe and the safety rules below so this is quick and safe to do per session.
Working recipe (lavish)
-
Publish the loopback port to the tailnet over plain HTTP:
sudo tailscale serve --bg --http=<port> <port>
Remove it when done with sudo tailscale serve --http=<port> off (or sudo tailscale serve reset).
-
Launch lavish so it accepts the tailnet host and emits tailnet URLs. These env vars are read at server start, so stop and relaunch lavish to change them:
LAVISH_AXI_ALLOWED_HOSTS='myrmex.taila827d7.ts.net myrmex' \
LAVISH_AXI_PORT=<port> \
LAVISH_AXI_LINK_HOST=myrmex.taila827d7.ts.net \
<launch lavish>
Resulting session URL: http://myrmex.taila827d7.ts.net:<port>/session/<id>
(Tailnet: DNS myrmex.taila827d7.ts.net, IP 100.119.99.32.)
Generalize beyond lavish
The same shape applies to any loopback-bound local server: local server on loopback -> tailscale serve -> tailnet-reachable, minding each server's own host binding and any host allowlist it enforces.
Safety rules the skill MUST encode
- Session-scoped only. Serve it up for the session and tear it down when done. Do NOT persist the serve config or bake it into box configuration.
- Keep servers on loopback. Never bind
0.0.0.0 (e.g. never LAVISH_AXI_HOST=0.0.0.0), which would serve arbitrary local files to the network. tailscale serve bridges loopback to the tailnet without changing the server's own binding.
- Never
tailscale funnel. Funnel exposes the service to the public internet; only tailscale serve (tailnet-private) is allowed.
What the skill teaches/automates
The serve recipe, the lavish env vars, teardown of the serve config, and the safety rules above.
Proposal
Add a skill that teaches firstmate how to serve lavish - and other loopback-bound local servers spawned on the box - over Tailscale, so they are reachable from the captain's Mac/phone without exposing anything to the public internet.
Why
Lavish (and similar tools) bind to loopback only, so their session URLs are not reachable from another device. A naive reverse proxy also fails because lavish enforces a host allowlist and returns
403 forbidden hostfor an unrecognizedHostheader. The skill should encode the working recipe and the safety rules below so this is quick and safe to do per session.Working recipe (lavish)
Publish the loopback port to the tailnet over plain HTTP:
Remove it when done with
sudo tailscale serve --http=<port> off(orsudo tailscale serve reset).Launch lavish so it accepts the tailnet host and emits tailnet URLs. These env vars are read at server start, so stop and relaunch lavish to change them:
Resulting session URL:
http://myrmex.taila827d7.ts.net:<port>/session/<id>(Tailnet: DNS
myrmex.taila827d7.ts.net, IP100.119.99.32.)Generalize beyond lavish
The same shape applies to any loopback-bound local server:
local server on loopback -> tailscale serve -> tailnet-reachable, minding each server's own host binding and any host allowlist it enforces.Safety rules the skill MUST encode
0.0.0.0(e.g. neverLAVISH_AXI_HOST=0.0.0.0), which would serve arbitrary local files to the network.tailscale servebridges loopback to the tailnet without changing the server's own binding.tailscale funnel. Funnel exposes the service to the public internet; onlytailscale serve(tailnet-private) is allowed.What the skill teaches/automates
The serve recipe, the lavish env vars, teardown of the serve config, and the safety rules above.