fix(browser): recover stale CDP sessions

Closed
MA
4mo ago
+608-14

Problem

A flattened CDP target session can disappear while the browser-level WebSocket and page target remain usable. Reopening the root socket does not repair that target session, and an obsolete socket can still reject calls owned by a replacement socket.

Recovery also must not replay an arbitrary command on a different page. A rejected click, navigation, or evaluation is safe to retry only after reattaching the exact original target.

Change

  • Treat no-argument connect() as ensure-connected, preserving a healthy socket and active target.
  • Scope pending calls and close handling to the WebSocket that owns them.
  • On Chrome error -32001, serialize recovery, list targets at browser level, and reattach the exact original page.
  • Restore only domains that were enabled on the stale session.
  • Retry the rejected command once only after exact-target reattachment.
  • If the original target closed or is unknown, return a clear error without creating another page or replaying the command.
  • Never replay after an ambiguous socket drop.

Reproduction

The tests use a local synthetic CDP WebSocket:

  1. Attach page-1 and return session-1.
  2. Reject a page command with CDP -32001: Session with given id not found.
  3. Keep page-1 in Target.getTargets.
  4. Verify one reattachment to page-1, domain restoration, and one successful retry.

A second case removes page-1 before recovery and verifies that a side-effecting command is sent only once, no blank page is created, and no other target receives the command.

Validation

  • bun test in packages/bcode-browser: 21 pass, 8 environment-gated skips
  • bun typecheck in packages/bcode-browser
  • Pre-push filtered typecheck: 13/13 packages pass
  • git diff --check