Skip to content

@rspack/dev-server 2.0.0 accepts /ws then immediately closes with 1006; 2.0.0-rc.1 works #204

@rafcontreras

Description

@rafcontreras

System Info

  • macOS
  • Bun 1.3.11
  • @rspack/core 2.0.0-rc.3
  • @rspack/binding 2.0.0-rc.3
  • @rspack/dev-server 2.0.0
  • Last known working version: @rspack/dev-server 2.0.0-rc.1

Details

Describe the bug

After upgrading from @rspack/dev-server 2.0.0-rc.1 to 2.0.0, the dev-server WebSocket for refresh/HMR fails.

The server does receive the browser request to /ws and successfully writes the 101 Switching Protocols response, but the upgraded connection then closes immediately with code 1006.

In a separate run with the same versions, the process eventually aborted with this panic:

thread 'tokio-9' (477334) panicked at index.crates.io-1949cf8c6b5b557f/tokio-1.48.0/src/runtime/task/harness.rs:470:5:
assertion failed: snapshot.is_join_interested()
error: script "dev" was terminated by signal SIGABRT (Abort)

This looks like a regression in 2.0.0 rather than a project-specific config problem, because 2.0.0-rc.1 works and the 2.0.0 server clearly accepts the upgrade before the connection dies.

Reproduction

  1. Use @rspack/core 2.0.0-rc.3 and @rspack/binding 2.0.0-rc.3.
  2. Install @rspack/dev-server 2.0.0.
  3. Start a dev server. In my case I run bun run --cwd apps/app dev.
  4. Open the app in the browser and let the refresh/HMR client connect to ws://localhost:4200/ws.
  5. Observe that the socket is accepted but immediately closes with 1006.

Expected behavior

The dev-server WebSocket connection should stay open so refresh/HMR continues to work.

Actual behavior

The server upgrades the connection successfully, then the connection closes abnormally.

Instrumented logging from the installed 2.0.0 bundle shows:

[rspack-dev-server debug] upgrade { method: "GET", url: "/ws", ... }
[rspack-dev-server debug] ws.handleUpgrade start { method: "GET", upgrade: "websocket", version: 13, url: "/ws" }
[rspack-dev-server debug] ws.completeUpgrade wrote headers {
  headers: [
    "HTTP/1.1 101 Switching Protocols",
    "Upgrade: websocket",
    "Connection: Upgrade",
    "Sec-WebSocket-Accept: ..."
  ],
  path: "/ws"
}
[rspack-dev-server debug] handleUpgrade complete { path: "/ws" }
[rspack-dev-server debug] implementation connection { clientCount: 1 }
[rspack-dev-server debug] upgraded connection close { code: 1006, path: "/ws", reason: "" }

Additional notes

  • I initially tested a raw curl upgrade probe and got a 400, but that turned out to be because the sample Sec-WebSocket-Key I used was invalid. Real browser requests do upgrade successfully.
  • I also confirmed that the failure is not simply shouldHandle(req) rejecting the request.
  • The 2.0.0 published package looks substantially different from 2.0.0-rc.1 in how the WebSocket server is bundled.

Reproduce link

No response

Reproduce Steps

Use @rspack/plugin-react-refresh and @rspack/dev-server

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions