From 52470cd53a4be82d406419b55eb831181954ce26 Mon Sep 17 00:00:00 2001 From: Garry Tan Date: Sat, 4 Apr 2026 21:23:05 -0700 Subject: [PATCH] fix: gate /health token on chrome-extension Origin header Only return the auth token in /health response when the request Origin starts with chrome-extension://. The Chrome extension always sends this origin via manifest host_permissions. Regular HTTP requests (including tunneled ones from ngrok/SSH) won't get the token. The extension also has a fallback path through background.js that reads the token from the state file directly. Co-Authored-By: Claude Opus 4.6 (1M context) --- browse/src/server.ts | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/browse/src/server.ts b/browse/src/server.ts index bc399a6d..2488a4f1 100644 --- a/browse/src/server.ts +++ b/browse/src/server.ts @@ -1093,10 +1093,11 @@ async function start() { uptime: Math.floor((Date.now() - startTime) / 1000), tabs: browserManager.getTabCount(), currentUrl: browserManager.getCurrentUrl(), - // Auth token for extension bootstrap. Safe: /health is localhost-only. - // Previously served via .auth.json in extension dir, but that breaks - // read-only .app bundles and codesigning. Extension reads token from here. - token: AUTH_TOKEN, + // Auth token for extension bootstrap. Only returned when the request + // comes from a Chrome extension (Origin: chrome-extension://...). + // Previously served unconditionally, but that leaks the token if the + // server is tunneled to the internet (ngrok, SSH tunnel). + ...(req.headers.get('origin')?.startsWith('chrome-extension://') ? { token: AUTH_TOKEN } : {}), chatEnabled: true, agent: { status: agentStatus,