diff --git a/website/docs/user-guide/desktop.md b/website/docs/user-guide/desktop.md index 8c64720ab..2c6cb7f91 100644 --- a/website/docs/user-guide/desktop.md +++ b/website/docs/user-guide/desktop.md @@ -111,13 +111,50 @@ By default the app starts and manages its own **local** backend. You can instead - **Remote URL** — the backend's dashboard URL, e.g. `http://:9119` - **Session token** — the backend's dashboard session token -The session token is the part that trips people up. **Hermes does not print it for you to copy** — by default the backend mints a fresh random token on every boot and injects it straight into the served HTML, so there is nothing in `config.yaml`, in `/gateway`, or in the logs to grab. For a remote connection you pin the token yourself on the backend (via `HERMES_DASHBOARD_SESSION_TOKEN`), run the backend with `--insecure`, then paste that same value into the app. +The session token is the part that trips people up. **Hermes does not print it for you to copy** — by default the backend mints a fresh random token on every boot and injects it straight into the served HTML, so there is nothing in `config.yaml`, in `/gateway`, or in the logs to grab. For a remote connection you pin the token yourself on the backend, then paste that same value into the app. -The full backend setup — minting the token, the `--insecure`-vs-OAuth-gate detail, the `HERMES_DESKTOP_REMOTE_URL` / `HERMES_DESKTOP_REMOTE_TOKEN` environment-variable override, Tailscale guidance, and a troubleshooting list — lives on the dashboard page, since the desktop app talks to the same backend the web dashboard does: +### On the backend (the remote machine) -➜ **[Web Dashboard → Connecting Hermes Desktop to a remote backend](./features/web-dashboard.md#connecting-hermes-desktop-to-a-remote-backend)** +```bash +# 1. Mint a stable token and store it in ~/.hermes/.env (secrets file, 0600). +# Without HERMES_DASHBOARD_SESSION_TOKEN the token is random per boot and +# uncopyable; setting it pins the value the desktop app will use. +TOKEN=$(openssl rand -base64 32) +echo "HERMES_DASHBOARD_SESSION_TOKEN=$TOKEN" >> ~/.hermes/.env +chmod 600 ~/.hermes/.env +echo "$TOKEN" # copy this value into the desktop app -The relevant environment variables are also catalogued under [Environment Variables → Web Dashboard & Hermes Desktop](../reference/environment-variables.md#web-dashboard--hermes-desktop). +# 2. Run the dashboard bound to a reachable address. +# --insecure is required for any non-loopback bind and keeps the legacy +# session-token auth path (a non-loopback bind WITHOUT --insecure engages +# the OAuth gate, which ignores the session token). +hermes dashboard --no-open --insecure --host 0.0.0.0 --port 9119 +``` + +Running the dashboard as a systemd service? Give the unit `EnvironmentFile=%h/.hermes/.env` so the token is in the environment at boot. + +:::warning +`--insecure` exposes a port that reads/writes your `.env` (API keys, secrets) and can run agent commands. Never expose it to the open internet — put it behind a VPN. [Tailscale](https://tailscale.com/) is the clean option: bind to the machine's tailscale IP (`--host `) and use `http://:9119` as the Remote URL so only your tailnet can reach it. +::: + +### In the app + +**Settings → Gateway → Remote gateway:** + +1. **Remote URL** — `http://:9119` (path prefixes like `/hermes` work if you front it with a reverse proxy) +2. **Session token** — paste the `$TOKEN` value from step 1 +3. **Test remote** — confirms the backend is reachable and the token is accepted +4. **Save and reconnect** — switches the desktop shell onto the remote backend + +The token is stored encrypted in the app's local config; leave the field blank on a later edit to keep the saved one. You can also set it without the UI via the `HERMES_DESKTOP_REMOTE_URL` + `HERMES_DESKTOP_REMOTE_TOKEN` environment variables before launching the app (both must be set together; they override the in-app settings). + +### Troubleshooting + +- **Test fails with 401** — the token doesn't match the backend's `HERMES_DASHBOARD_SESSION_TOKEN`, or the backend is bound non-loopback *without* `--insecure` (OAuth gate is on, ignoring the token). Verify with `curl -s -H "X-Hermes-Session-Token: $TOKEN" http://:9119/api/status` — that should return JSON, not a 401. +- **Connection refused / times out** — the backend bound to `127.0.0.1` (the default) or a firewall/VPN is blocking the port. Bind to `0.0.0.0` or the tailscale IP and open the port to your trusted network. +- **No token to copy** — expected. You mint it yourself; Hermes never surfaces the default ephemeral one. + +For the same setup from the web-dashboard angle, see [Web Dashboard → Connecting Hermes Desktop to a remote backend](./features/web-dashboard.md#connecting-hermes-desktop-to-a-remote-backend); the env vars are catalogued under [Environment Variables → Web Dashboard & Hermes Desktop](../reference/environment-variables.md#web-dashboard--hermes-desktop). ## Troubleshooting