| Side | What it does |
|---|---|
| Share this machine | Expose the running app so a phone, a LAN device, or another Mains can drive it |
| Connect to a backend | Point this app at a remote backend over an SSH tunnel or a direct WebSocket URL |
Local mode is the zero-config default. Relay is opt-in, and only one backend is active at a time — switching is instant and never touches your local data.
How It Works
Every call in Mains — queries, run events, terminal streams, tool approvals — already flows through one uniform seam (window.api). Relay swaps the transport behind that seam from in-process IPC to a WebSocket, so the entire app surface works against a remote backend with no feature loss.
| Runs on the backend | Stays local |
|---|---|
Provider CLIs (claude, codex, copilot, cursor) and their login state | The renderer / UI |
| Git, worktrees, and the workspace files | The browser panel and inputs |
Terminals (node-pty) | Settings UI |
| The SQLite database and encrypted connection secrets | — |
Connection Status
The active backend shows a live status dot:| Status | Meaning |
|---|---|
connected | The WebSocket is open and the UI is live |
connecting | First connection in progress |
reconnecting | Link dropped — backing off and retrying |
offline | No connection (local mode is always connected) |
Web Client
A backend that exposes itself can also be opened in a plain browser — a phone or tablet loads the same Mains UI over the network. See Share This Machine for enabling it. In the web client, you’re already connected to the backend that served the page; adding or switching backends is a desktop-app concern.Where To Start
Watch a remote dev box from your laptop
Use an SSH tunnel — the secure, zero-infrastructure path. Nothing is exposed on the network.
Reach your desktop from a phone or another device
Share this machine over LAN or Tailscale HTTPS, then open the web URL or connect directly.
Security Model
- SSH tunnel — traffic is encrypted and authenticated by SSH; the backend only listens on
127.0.0.1. No ports on the network. - Direct / LAN / Tailscale — guarded by a pairing token. Never expose a tokenless backend on a routable interface.
- Local-only controls — the toggles that expose a machine are registered on local IPC only, so a connected remote client can’t change the exposure it’s riding on.
