openclaw/openclaw · error · Error
Browser control is disabled
Error message
Browser control is disabled
What it means
Thrown by resolveGatewayBridge when an extension-relay Gateway upgrade arrives but Browser control cannot be obtained: getBrowserControlState() is null and startBrowserControlServiceFromConfig() also returns null. A null return means the bundled Browser plugin is effectively disabled (config browser.enabled=false, plugins.browser disabled, or resolved.enabled=false) or browser auth could not be auto-configured. This guards the WebSocket upgrade path so a connecting Chrome extension gets a deterministic failure instead of a half-bound relay.
Source
Thrown at extensions/browser/src/browser/extension-relay/gateway-relay-route.ts:69
function requestedProfileName(resource: string, fallback: string): string {
return new URL(resource, "http://127.0.0.1").searchParams.get("profile") ?? fallback;
}
function defaultExtensionProfileName(profiles: Record<string, { driver?: string }>): string {
for (const [name, profile] of Object.entries(profiles)) {
if (profile.driver === "extension") {
return name;
}
}
return "chrome";
}
async function resolveGatewayBridge(resource: string) {
let state = getBrowserControlState();
if (!state) {
state = await startBrowserControlServiceFromConfig();
if (!state) {
throw new Error("Browser control is disabled");
}
}
const profileName = requestedProfileName(
resource,
defaultExtensionProfileName(state.resolved.profiles),
);
const resolved = resolveProfile(state.resolved, profileName);
if (!resolved || resolved.driver !== "extension") {
throw new Error(`Extension browser profile "${profileName}" was not found`);
}
return {
bridge: (await ensureExtensionRelayForProfile(state, resolved)).bridge,
profileName,
};
}
/** Handle the plugin-owned Gateway upgrade path. */
export async function handleGatewayExtensionUpgrade(View on GitHub (pinned to 01804a7531)
Solutions
- Verify openclaw.json does not set browser.enabled=false and that plugins.browser is not disabled; run `openclaw configure` or check `openclaw doctor`.
- Confirm the bundled browser plugin is enabled (enabledByDefault is true) and no plugins.browser.enabled=false override exists.
- If browser control is intentionally disabled, uninstall or disconnect the Chrome extension so it stops attempting the relay upgrade.
- Re-run `openclaw browser extension pair` after re-enabling to confirm the relay secret and extension handshake work end to end.
Example fix
// before (openclaw.json)
{
"browser": { "enabled": false }
}
// after
{
"browser": { "enabled": true }
} Defensive patterns
Strategy: validation
Validate before calling
import { getRuntimeConfig } from '../config/config.js';
import { isDefaultBrowserPluginEnabled } from '../plugin-enabled.js';
function assertBrowserControlStartable(): void {
const cfg = getRuntimeConfig();
if (!isDefaultBrowserPluginEnabled(cfg)) {
throw new Error('Browser plugin is disabled in config; cannot start Browser control');
}
if (cfg.browser?.enabled === false) {
throw new Error('browser.enabled=false; cannot start Browser control');
}
}
// Call before issuing extension-relay upgrade or local dispatch. Try / catch
try {
const { bridge, profileName } = await resolveGatewayBridge(resource);
// ...
} catch (err) {
if (err instanceof Error && err.message === 'Browser control is disabled') {
destroy(socket, '503 Service Unavailable'); // surface to extension as transient
return;
}
throw err;
} Prevention
- Validate browser plugin enablement in onboarding/startup before accepting extension upgrades.
- Expose a doctor check that warns when the extension is paired but the plugin is disabled.
- Treat 'Browser control is disabled' as a config-state error, not a transient one — do not retry without a config change.
When it happens
Trigger: Occurs during handleGatewayExtensionUpgrade (the /browser/extension WebSocket path) when: (a) openclaw.json sets browser.enabled=false; (b) plugins.browser.enabled=false; (c) the Browser plugin is disabled by normalizePluginsConfig; or (d) resolveBrowserConfig yields enabled=false. The check runs after origin and token validation succeed, inside prepareAuthenticated (v2) or the legacy resolveGatewayBridge call.
Common situations: Operators who explicitly disabled the browser plugin but still have the Chrome extension installed and attempting to connect; environments where a prior plugin was disabled via plugins config; CI/test harnesses that load a stripped config; configs where browser.enabled was set false during a security lockdown without removing the extension pairing.
Related errors
- Extension browser profile "${profileName}" was not found
- browser control disabled
- browser.executablePath not found: ${resolved.executablePath}
- browser.executablePath must point to the browser executable,
- No available extension relay ports in the reserved browser r
AI-assisted analysis of openclaw/openclaw@01804a7531 (2026-08-12).
Data as JSON: /api/errors/ada76b35fe8e2273.
Report an issue: GitHub.