← Back to PRs

#19026: fix(gateway): use loopback for local CLI-to-gateway connections

by Phineas1500 open 2026-02-17 08:11 View on GitHub →
gateway commands size: S
## Summary Fixes #19004. - When `gateway.bind=lan`, the CLI constructed its WebSocket URL using the host's LAN IP (e.g. `ws://192.168.1.42:18789`). The gateway's `isLocalDirectRequest()` only recognizes loopback/localhost Host headers as "local", so the CLI was treated as a remote connection requiring device pairing — a chicken-and-egg problem. - `localUrl` now always uses `127.0.0.1`. The `urlSource` diagnostic string still reports the LAN/tailnet IP for display purposes. - The `bind` mode controls which interfaces the **server** listens on — `0.0.0.0` always accepts loopback, so co-located clients should always connect via loopback. ## Test plan - [x] `npx vitest run src/gateway/call.test.ts` — all 21 tests pass - [x] `npx oxfmt --check` and `npx oxlint` — clean - [x] Manual CLI test: set `gateway.bind=lan`, ran `gateway probe` and `gateway health` — connects via `ws://127.0.0.1:18789` and all channels report OK <!-- greptile_comment --> <h3>Greptile Summary</h3> Fixes a chicken-and-egg problem where the CLI, when configured with `gateway.bind=lan` or `bind=tailnet`, would construct WebSocket URLs using the LAN/tailnet IP (e.g., `ws://192.168.1.42:18789`). The gateway's `isLocalDirectRequest()` only recognizes loopback/localhost Host headers as local, so the CLI was incorrectly treated as a remote connection requiring device pairing. - `localUrl` in `buildGatewayConnectionDetails` now always uses `127.0.0.1`. Since LAN mode binds to `0.0.0.0` (which accepts loopback), co-located CLI clients connect correctly. - The `urlSource` diagnostic string still reports the LAN/tailnet IP for display purposes, preserving useful debugging output. - Tests updated to match new behavior, though three test names are now misleading (they describe old tailnet/LAN behavior while asserting loopback URLs). <h3>Confidence Score: 4/5</h3> - This PR is safe to merge — it's a focused, well-reasoned fix for a clear bug with no risk of regression. - The change is minimal and directly addresses the documented issue. The logic is sound: LAN/tailnet bind modes use `0.0.0.0` which accepts loopback, so local CLI clients should always connect via loopback to pass the `isLocalDirectRequest()` check. Only style concern is the now-misleading test names. - No files require special attention. `src/gateway/call.test.ts` has minor test naming issues but no logic problems. <sub>Last reviewed commit: f335df4</sub> <!-- greptile_other_comments_section --> <!-- /greptile_comment -->

Most Similar PRs