diff --git a/extensions/browser/src/browser/server.control-server.test-harness.ts b/extensions/browser/src/browser/server.control-server.test-harness.ts index 5f02544f816..310dd7476d4 100644 --- a/extensions/browser/src/browser/server.control-server.test-harness.ts +++ b/extensions/browser/src/browser/server.control-server.test-harness.ts @@ -1,4 +1,5 @@ import { afterEach, beforeEach, vi } from "vitest"; +import { deriveDefaultBrowserCdpPortRange } from "../config/port-defaults.js"; import type { MockFn } from "../test-utils/vitest-mock-fn.js"; import { installChromeUserDataDirHooks } from "./chrome-user-data-dir.test-harness.js"; import { getFreePort } from "./test-port.js"; @@ -375,9 +376,13 @@ function makeProc(pid = 123) { const proc = makeProc(); +function defaultBrowserCdpPortForState(testPort: number): number { + return deriveDefaultBrowserCdpPortRange(testPort).start; +} + function defaultProfilesForState(testPort: number): HarnessState["cfgProfiles"] { return { - openclaw: { cdpPort: testPort + 9, color: "#FF4500" }, + openclaw: { cdpPort: defaultBrowserCdpPortForState(testPort), color: "#FF4500" }, }; } @@ -520,7 +525,7 @@ export async function resetBrowserControlServerTestContext(): Promise { mockClearAll(chromeMcpMocks); state.testPort = await getFreePort(); - state.cdpBaseUrl = `http://127.0.0.1:${state.testPort + 9}`; + state.cdpBaseUrl = `http://127.0.0.1:${defaultBrowserCdpPortForState(state.testPort)}`; state.cfgProfiles = defaultProfilesForState(state.testPort); state.prevGatewayPort = process.env.OPENCLAW_GATEWAY_PORT; process.env.OPENCLAW_GATEWAY_PORT = String(state.testPort - 2); diff --git a/src/config/port-defaults.test.ts b/src/config/port-defaults.test.ts new file mode 100644 index 00000000000..a68b0729c3e --- /dev/null +++ b/src/config/port-defaults.test.ts @@ -0,0 +1,22 @@ +import { describe, expect, it } from "vitest"; +import { + DEFAULT_BROWSER_CDP_PORT_RANGE_END, + DEFAULT_BROWSER_CDP_PORT_RANGE_START, + deriveDefaultBrowserCdpPortRange, +} from "./port-defaults.js"; + +describe("port defaults", () => { + it("derives the browser CDP range from the control port", () => { + expect(deriveDefaultBrowserCdpPortRange(18791)).toEqual({ + start: DEFAULT_BROWSER_CDP_PORT_RANGE_START, + end: DEFAULT_BROWSER_CDP_PORT_RANGE_END, + }); + }); + + it("keeps the default browser CDP range wide when derived ports would overflow", () => { + expect(deriveDefaultBrowserCdpPortRange(65440)).toEqual({ + start: DEFAULT_BROWSER_CDP_PORT_RANGE_START, + end: DEFAULT_BROWSER_CDP_PORT_RANGE_END, + }); + }); +}); diff --git a/src/config/port-defaults.ts b/src/config/port-defaults.ts index 8e5321cb8d4..ac21045168d 100644 --- a/src/config/port-defaults.ts +++ b/src/config/port-defaults.ts @@ -17,6 +17,8 @@ export const DEFAULT_BROWSER_CONTROL_PORT = 18791; export const DEFAULT_CANVAS_HOST_PORT = 18793; export const DEFAULT_BROWSER_CDP_PORT_RANGE_START = 18800; export const DEFAULT_BROWSER_CDP_PORT_RANGE_END = 18899; +const DEFAULT_BROWSER_CDP_PORT_RANGE_SPAN = + DEFAULT_BROWSER_CDP_PORT_RANGE_END - DEFAULT_BROWSER_CDP_PORT_RANGE_START; export function deriveDefaultBridgePort(gatewayPort: number): number { return derivePort(gatewayPort, 1, DEFAULT_BRIDGE_PORT); @@ -32,12 +34,12 @@ export function deriveDefaultCanvasHostPort(gatewayPort: number): number { export function deriveDefaultBrowserCdpPortRange(browserControlPort: number): PortRange { const start = derivePort(browserControlPort, 9, DEFAULT_BROWSER_CDP_PORT_RANGE_START); - const end = clampPort( - start + (DEFAULT_BROWSER_CDP_PORT_RANGE_END - DEFAULT_BROWSER_CDP_PORT_RANGE_START), - DEFAULT_BROWSER_CDP_PORT_RANGE_END, - ); - if (end < start) { - return { start, end: start }; + const end = start + DEFAULT_BROWSER_CDP_PORT_RANGE_SPAN; + if (end <= 65535) { + return { start, end }; } - return { start, end }; + return { + start: DEFAULT_BROWSER_CDP_PORT_RANGE_START, + end: DEFAULT_BROWSER_CDP_PORT_RANGE_END, + }; }