Context
vitejs/devtools#520 ("fix(core): allocate standalone WebSocket ports atomically") by @webfansplz fixed vitejs/devtools#517 (parallel Vitest runs crashing with EADDRINUSE because the standalone WS port was probed-then-bound instead of bound atomically). Its diff was against packages/core/src/client-adjacent node code — packages/core/src/node/ws.ts — which no longer exists in vitejs/devtools: the v0.9 migration retired the bespoke WS server there in favor of this repo's initHub/WsRpcTransport.
The core fix already shipped here — #171 ("fix: atomically allocate standalone ws ports"), merged 2026-08-06, binds standalone WsRpcTransport servers to port 0 and lets the OS pick atomically. It's already included in the devframe@0.9.0-beta.2 that vitejs/devtools now depends on, so the EADDRINUSE race itself is resolved.
What's unverified is the other half of #520's diff: "publish the WebSocket endpoint and refresh remote docks after the port is resolved" — in the old ws.ts, once the atomic bind returned a port, the code rebuilt contextInternal.wsEndpoint and re-emitted dock:entry:updated for every registered remote iframe dock so their connection URLs picked up the real port. That responsibility now lives in this repo's hub-internals (getInternalContext / remote-dock token + WS-endpoint metadata, per vitejs/devtools's AGENTS.md) and @devframes/hub/client's connectRemoteDevframe/parseRemoteConnection — not in vitejs/devtools anymore.
Diff: https://github.com/vitejs/devtools/pull/520/files
For agents picking this up
Context
vitejs/devtools#520 ("fix(core): allocate standalone WebSocket ports atomically") by @webfansplz fixed vitejs/devtools#517 (parallel Vitest runs crashing with
EADDRINUSEbecause the standalone WS port was probed-then-bound instead of bound atomically). Its diff was againstpackages/core/src/client-adjacent node code —packages/core/src/node/ws.ts— which no longer exists in vitejs/devtools: the v0.9 migration retired the bespoke WS server there in favor of this repo'sinitHub/WsRpcTransport.The core fix already shipped here — #171 ("fix: atomically allocate standalone ws ports"), merged 2026-08-06, binds standalone
WsRpcTransportservers to port0and lets the OS pick atomically. It's already included in thedevframe@0.9.0-beta.2that vitejs/devtools now depends on, so theEADDRINUSErace itself is resolved.What's unverified is the other half of #520's diff: "publish the WebSocket endpoint and refresh remote docks after the port is resolved" — in the old
ws.ts, once the atomic bind returned a port, the code rebuiltcontextInternal.wsEndpointand re-emitteddock:entry:updatedfor every registered remote iframe dock so their connection URLs picked up the real port. That responsibility now lives in this repo's hub-internals (getInternalContext/ remote-dock token + WS-endpoint metadata, per vitejs/devtools'sAGENTS.md) and@devframes/hub/client'sconnectRemoteDevframe/parseRemoteConnection— not in vitejs/devtools anymore.Diff: https://github.com/vitejs/devtools/pull/520/files
For agents picking this up
WsRpcTransport/hub instance that binds to an OS-assigned port (port: 0) correctly re-publishes its resolved WS endpoint to already-registered remote docks once bound, the way oldws.tsdid withdock:entry:updated. If there's a gap — e.g. a remote dock registered beforehub.readyresolves ends up with a stale/empty connection URL — fix it inpackages/hub/src/node/initiate.tsor the relevant hub-internals path.Co-authored-by: webfansplz <...>trailer (look up their GitHub noreply email, or omit if unavailable) and mention them in the PR description.