test(browse): daemon-state and refusal e2e for the explicit direct opt-out; headed env and BROWSER.md contract checks (#3440 item 8)

Co-authored-by: capy-ai[bot] <230910855+capy-ai[bot]@users.noreply.github.com>
This commit is contained in:
garrytanandcapy-ai[bot] committed 2026-10-26 03:36:51 +00:00
1 parent cadf2bcb92
commit c08c586bbd
4 files changed
+60 -2

No files matched your search

+1 -1
View File
@@ -146,7 +146,7 @@ jobs:
resolved="$(realpath "$tmp")"
echo "temp root: $tmp -> $resolved"
test "$resolved" != "${tmp%/}"
files=(test/gstack-design-detect.test.ts browse/test/chromium-profile-isolation.test.ts test/cso-git-hardening.test.ts test/plan-count-file-permission.test.ts test/spec-quality-gate-secret-sink.test.ts test/gstack-memory-ingest.test.ts test/regression-issue3024-zsh-sourced-helpers.test.ts test/codex-probe-subcommands.test.ts)
files=(test/gstack-design-detect.test.ts browse/test/chromium-profile-isolation.test.ts test/cso-git-hardening.test.ts test/plan-count-file-permission.test.ts test/spec-quality-gate-secret-sink.test.ts test/gstack-memory-ingest.test.ts test/regression-issue3024-zsh-sourced-helpers.test.ts test/codex-probe-subcommands.test.ts browse/test/proxy-env-daemon.test.ts)
for file in "${files[@]}"; do test -f "$file"; done
bun test "${files[@]}"
+1
View File
@@ -16,6 +16,7 @@
- `browse/test/proxy-direct-launch-paths.test.ts` (Linux, real Chromium under Xvfb): the `BROWSE_EXTENSIONS_DIR` persistent context, `launchHeaded()` and the `handoff()` relaunch each ignore an inherited `HTTPS_PROXY` (no CONNECT, `ERR_NAME_NOT_RESOLVED`), and a headed control with a configured proxy still sends the CONNECT to it.
- `browse/test/proxy-config.test.ts`: `forcesDirect` per platform, and `directProxyLogLine` for the Linux variable list, the explicit-direct line on macOS/Windows, and the system-proxy line.
- `browse/test/proxy-env.test.ts`, `browse/test/restart-env.test.ts`: the config hash separates an explicit direct from no proxy on macOS and Windows and not on Linux (`extractGlobalFlags` takes the platform); the mismatch refusal for both directions (explicit session against a system-proxy daemon, default session against an explicit-direct daemon); `buildRestartEnv` re-emits `BROWSE_PROXY_URL=direct` from the invocation or the persisted state, and a proxied invocation wins over it.
- `browse/test/proxy-env-daemon.test.ts`: through the real CLI and daemon, `BROWSE_PROXY_URL=direct` is written to the daemon state as `proxyDirect` where it bypasses the system proxy and a default session is then refused with the `BROWSE_PROXY_URL differs` lines; on Linux the daemon is reused. The file joins the macOS named-regressions CI job so the refusal arm runs there. `buildHeadedServerEnv` carries the opt-out to the headed server, and BROWSER.md's section is checked against the real switch and log literals.
- `browse/test/proxy-direct-launch-args.test.ts`: reads the real command line of the headless Chromium `BrowserManager` launched (from the pid it records) and asserts the switch is present on Linux and absent elsewhere without an opt-out, and present on every platform with `BROWSE_PROXY_URL=direct`; the per-platform expectations are written out, not read back from `forcesDirect`. Skipped on Windows, where no command line reader exists.
## [1.91.226.0] - 2026-10-26
+31
View File
@@ -134,4 +134,35 @@ describe.skipIf(process.platform === 'win32')('#915 proxy from the environment,
expect(proxiedHosts.length).toBe(before);
expect(JSON.parse(fs.readFileSync(stateFile, 'utf8')).proxy).toBeUndefined();
}, 120_000);
// Added by: /ship test coverage audit (Capy), 2026-10-25, for #3440 item 8.
// Value: protects=the daemon state records BROWSE_PROXY_URL=direct where it bypasses the system proxy settings, and a default session there is refused, not handed the opt-out;
// fails_when=server.ts drops proxyDirect from the state, the CLI hash stops carrying the opt-out, or Linux starts refusing a reused daemon over it;
// why_new=proxy-env.test.ts drives proxyMismatchLines with a hand-built state; nothing reads the state the daemon wrote or runs the refusal through the CLI;
// seam=none; no_claim=Chromium's proxy behaviour (loopback page only); the proxyDirect=true write and the refusal arm run on the macOS named-regressions CI job and on a Windows checkout, the Linux lanes run the reuse arm
test('BROWSE_PROXY_URL=direct is daemon state where it bypasses the system proxy, and a default session is refused there (#3440)', async () => {
expect((await browse(['stop'], {})).code).toBe(0);
const r = await browse(['goto', `http://127.0.0.1:${direct.port}/`], { BROWSE_PROXY_URL: 'direct' });
expect(r.code, r.out).toBe(0);
expect(r.stderr).toContain('Starting server...');
const pid = daemonPid();
const bypassesSystemProxy = process.platform !== 'linux';
const state = JSON.parse(fs.readFileSync(stateFile, 'utf8'));
expect(state.proxy).toBeUndefined();
if (bypassesSystemProxy) expect(state.proxyDirect).toBe(true);
else expect(state.proxyDirect).toBeUndefined();
const plain = await browse(['text'], {});
if (bypassesSystemProxy) {
expect(plain.code).toBe(1);
expect(plain.stderr).toContain('different proxy settings (BROWSE_PROXY_URL differs)');
expect(plain.stderr).toContain('daemon: no proxy (BROWSE_PROXY_URL=direct)');
expect(plain.stderr).toContain('session: no proxy');
expect(plain.stderr).toContain('or set BROWSE_PROXY_URL=direct to use the running daemon without a proxy');
} else {
expect(plain.code, plain.out).toBe(0);
expect(plain.stderr).not.toContain('Starting server');
expect(plain.stdout).toContain('direct loopback page');
}
expect(daemonPid()).toBe(pid);
}, 120_000);
});
+27 -1
View File
@@ -3,7 +3,7 @@
* mismatch refusal. The daemon round trip is in proxy-env-daemon.test.ts.
*/
import { describe, expect, test } from 'bun:test';
import { computeConfigHash, noProxyToChromiumRules, parseProxyConfig, resolveProxy, serverProxyEnv, withLoopbackBypass } from '../src/proxy-config';
import { DIRECT_PROXY_ARG, computeConfigHash, directProxyLogLine, noProxyToChromiumRules, parseProxyConfig, resolveProxy, serverProxyEnv, withLoopbackBypass } from '../src/proxy-config';
import { buildHeadedServerEnv, buildRestartEnv, extractGlobalFlags, proxyMismatchLines, withLoopbackNoProxy } from '../src/cli';
describe('resolveProxy precedence', () => {
@@ -148,6 +148,17 @@ describe('server env carries the proxy source and bypass', () => {
expect(buildHeadedServerEnv(flags)).toMatchObject(expected);
expect(buildRestartEnv(extractGlobalFlags(['text'], {}), null).BROWSE_PROXY_URL).toBeUndefined();
});
// Added by: /ship test coverage audit (Capy), 2026-10-25, for #3440 item 8.
// Value: protects=a headed connect with BROWSE_PROXY_URL=direct on macOS/Windows hands its daemon the opt-out, so the headed daemon hashes and launches direct;
// fails_when=buildHeadedServerEnv spreads only proxyUrl/source/bypass and drops explicitDirect, or proxyServerEnv stops re-emitting it;
// why_new=restart-env.test.ts covers buildRestartEnv only and the headed case above is a proxied session; seam=none;
// no_claim=the headed daemon's launch itself (unit: only the env it is handed; on Linux the opt-out hashes like no proxy, so the env is empty by design)
test('a headed launch keeps BROWSE_PROXY_URL=direct where it bypasses the system proxy settings, and a --proxy still wins (#3440)', () => {
expect(buildHeadedServerEnv(extractGlobalFlags(['connect'], { BROWSE_PROXY_URL: 'direct' }, 'darwin')).BROWSE_PROXY_URL).toBe('direct');
expect(buildHeadedServerEnv(extractGlobalFlags(['connect'], { BROWSE_PROXY_URL: 'direct' }, 'linux')).BROWSE_PROXY_URL).toBeUndefined();
expect(buildHeadedServerEnv(extractGlobalFlags(['connect', '--proxy', 'http://p:1'], { BROWSE_PROXY_URL: 'direct' }, 'darwin')).BROWSE_PROXY_URL).toBe('http://p:1/');
});
});
describe('serverProxyEnv (the daemon side)', () => {
@@ -218,4 +229,19 @@ describe('BROWSER.md documents the proxy messages', () => {
expect(section).toContain(needle);
}
});
// Added by: /ship test coverage audit (Capy), 2026-10-25, for #3440 item 8.
// Value: protects=the section names the Chromium switch and the daemon-log line a user greps for, as the code emits them;
// fails_when=DIRECT_PROXY_ARG or the '[proxy] none:' log prefix is renamed without BROWSER.md, or the direct-mode paragraph is dropped;
// why_new=the #915 needles above predate the switch and the log line; seam=none;
// no_claim=prose accuracy beyond those two literals (doc-contract check only)
test('the direct-mode paragraph names the switch Chromium gets and the daemon-log line that records it (#3440)', async () => {
const doc = await Bun.file(new URL('../../BROWSER.md', import.meta.url)).text();
const section = doc.slice(doc.indexOf('\n### Proxy from environment\n'));
expect(section).toContain(DIRECT_PROXY_ARG);
for (const needle of ['browse-daemon.log', '[proxy] using <url> from', '[proxy] none: direct connection (', '[proxy] none: system proxy settings']) {
expect(section).toContain(needle);
}
expect(directProxyLogLine({ HTTPS_PROXY: 'http://b:2' }, 'linux')).toContain('[proxy] none: direct connection (' + DIRECT_PROXY_ARG + '; ignoring HTTPS_PROXY)');
});
});