feat: use the network source architecture (defineNetwork)#2650
Conversation
720e665 to
f65e91d
Compare
defineNetwork APIdefineNetwork API
1298da4 to
336a1bb
Compare
336a1bb to
7e2bf32
Compare
defineNetwork APIdefineNetwork API
There was a problem hiding this comment.
♻️ Duplicate comments (1)
src/browser/sources/service-worker-source.ts (1)
400-428:⚠️ Potential issue | 🟡 Minor
errorWith()silently ignores non-Error, non-Response throwables.If
reasonis neither aResponsenor anError(e.g., a thrown string, number, or plain object), the method returns without resolving the request. This could leave the request hanging indefinitely.🛡️ Proposed fix to handle arbitrary throwables
public errorWith(reason?: unknown): void { if (reason instanceof Response) { return this.respondWith(reason) } if (reason instanceof Error) { devUtils.warn( `Uncaught exception in the request handler for "%s %s". This exception has been gracefully handled as a 500 response, however, it's strongly recommended to resolve this error, as it indicates a mistake in your code. If you wish to mock an error response, please see this guide: https://mswjs.io/docs/http/mocking-responses/error-responses`, this.data.request.method, this.data.request.url, ) this.respondWith( HttpResponse.json( { name: reason.name, message: reason.message, stack: reason.stack, }, { status: 500, statusText: 'Request Handler Error', }, ), ) + return + } + + if (reason !== undefined) { + devUtils.warn( + `Uncaught non-Error value thrown in the request handler for "%s %s": %o. This has been gracefully handled as a 500 response.`, + this.data.request.method, + this.data.request.url, + reason, + ) + + this.respondWith( + HttpResponse.json( + { + name: 'UnknownError', + message: String(reason), + }, + { + status: 500, + statusText: 'Request Handler Error', + }, + ), + ) } }🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@src/browser/sources/service-worker-source.ts` around lines 400 - 428, The errorWith method currently returns silently for throwables that are neither Response nor Error, leaving requests unresolved; update errorWith (the method) to handle arbitrary throwables by adding an else branch that logs a warning via devUtils.warn (including this.data.request.method and this.data.request.url) and calls this.respondWith(HttpResponse.json(...)) returning a 500 response; construct the JSON body with a fallback name like "NonErrorThrown" (or use typeof reason), a message created by String(reason) or JSON.stringify when safe, and omit or set stack to undefined, so all thrown values resolve the request instead of hanging.
🧹 Nitpick comments (1)
src/browser/setup-worker.ts (1)
107-109: Consider stronger typing for theWebSocketInterceptorcast.The
as anycast obscures type incompatibilities. IfInterceptorSourceexpects a specific interceptor interface, consider updating the type definition or using a more precise cast to maintain type safety.🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@src/browser/setup-worker.ts` around lines 107 - 109, The current use of "as any" on new WebSocketInterceptor() hides type mismatches for InterceptorSource.interceptors; replace the any cast with the concrete interceptor interface expected by InterceptorSource (or make InterceptorSource generic) so the compiler enforces compatibility—either update WebSocketInterceptor to implement the required interface (methods/properties) or update the InterceptorSource type signature to accept the WebSocketInterceptor type, and then remove the "as any" cast from the interceptors array where new WebSocketInterceptor() is passed.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Duplicate comments:
In `@src/browser/sources/service-worker-source.ts`:
- Around line 400-428: The errorWith method currently returns silently for
throwables that are neither Response nor Error, leaving requests unresolved;
update errorWith (the method) to handle arbitrary throwables by adding an else
branch that logs a warning via devUtils.warn (including this.data.request.method
and this.data.request.url) and calls this.respondWith(HttpResponse.json(...))
returning a 500 response; construct the JSON body with a fallback name like
"NonErrorThrown" (or use typeof reason), a message created by String(reason) or
JSON.stringify when safe, and omit or set stack to undefined, so all thrown
values resolve the request instead of hanging.
---
Nitpick comments:
In `@src/browser/setup-worker.ts`:
- Around line 107-109: The current use of "as any" on new WebSocketInterceptor()
hides type mismatches for InterceptorSource.interceptors; replace the any cast
with the concrete interceptor interface expected by InterceptorSource (or make
InterceptorSource generic) so the compiler enforces compatibility—either update
WebSocketInterceptor to implement the required interface (methods/properties) or
update the InterceptorSource type signature to accept the WebSocketInterceptor
type, and then remove the "as any" cast from the interceptors array where new
WebSocketInterceptor() is passed.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Repository UI
Review profile: CHILL
Plan: Pro
Run ID: e56feca9-0dcd-4ef4-9fa9-0e963bc2ce5c
📒 Files selected for processing (3)
src/browser/setup-worker.tssrc/browser/sources/service-worker-source.tstest/browser/msw-api/setup-worker/life-cycle-events/on.test.ts
🚧 Files skipped from review as they are similar to previous changes (1)
- test/browser/msw-api/setup-worker/life-cycle-events/on.test.ts
There was a problem hiding this comment.
Actionable comments posted: 1
🧹 Nitpick comments (1)
src/core/experimental/define-network.test.ts (1)
28-28: Floating promises in async assertions could cause test runner warnings.The
toBeInstanceOf(Promise)assertions verify the return type but leave the returned Promises unhandled. While these empty async functions won't reject, some test runners flag unhandled promises. Consider awaiting or explicitly ignoring them for cleaner test output.💡 Example fix for one case
- expect(network.enable()).toBeInstanceOf(Promise) + const result = network.enable() + expect(result).toBeInstanceOf(Promise) + await resultAlso applies to: 40-40, 73-73, 87-87
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@src/core/experimental/define-network.test.ts` at line 28, Tests currently assert return types with expect(network.enable()).toBeInstanceOf(Promise) (and similarly for network.disable(), network.onRequest(), network.offRequest()), leaving Promises unawaited and creating floating promises; change each assertion to either await the call (e.g., await network.enable() then assert expected side-effects) or use Jest's promise helpers (await expect(network.enable()).resolves.toBeDefined() or similar) so the returned Promise is handled and no unhandled/floating promise warnings occur.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Inline comments:
In `@src/core/experimental/define-network.test.ts`:
- Line 16: Fix the typo in the test names in
src/core/experimental/define-network.test.ts: change the string "returns an
async enable if any the sources are async" to "returns an async enable if any of
the sources are async" (update both occurrences, including the one referenced
around the second occurrence) so the test descriptions read correctly; locate
the tests by the current description in the it(...) calls in the file.
---
Nitpick comments:
In `@src/core/experimental/define-network.test.ts`:
- Line 28: Tests currently assert return types with
expect(network.enable()).toBeInstanceOf(Promise) (and similarly for
network.disable(), network.onRequest(), network.offRequest()), leaving Promises
unawaited and creating floating promises; change each assertion to either await
the call (e.g., await network.enable() then assert expected side-effects) or use
Jest's promise helpers (await expect(network.enable()).resolves.toBeDefined() or
similar) so the returned Promise is handled and no unhandled/floating promise
warnings occur.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Repository UI
Review profile: CHILL
Plan: Pro
Run ID: 6bf9d467-fa56-4297-b0e0-4816c7bb266a
📒 Files selected for processing (4)
src/browser/glossary.tssrc/browser/index.tssrc/browser/setup-worker.tssrc/core/experimental/define-network.test.ts
✅ Files skipped from review due to trivial changes (2)
- src/browser/glossary.ts
- src/browser/index.ts
Released: v2.13.0 🎉This has been released in v2.13.0. Get these changes by running the following command: Predictable release automation by Release. |
msw 2.13 introduced a service-worker lifecycle change that breaks our vitest browser tests. Our per-test fixture calls worker.start()/stop() around each test; on 2.13 the stop → next start cycle leaves a window where requests bypass the worker and hit Vite directly, so the uuid lookup fails with "Failed to fetch" and dependent tests time out at 20s. This reproduces locally: upgrading to 2.13.3 fails ~13 tests; pinning back to 2.12.14 makes all 196 tests pass (~21s, matching baseline). Upstream bug: mswjs/msw#2706 Introduced by the 2.13.0 "network source architecture" refactor (mswjs/msw#2650). A follow-up PR will upgrade msw back to the latest and adjust the worker fixture to only start() once per test file (the recommended workaround: reset handlers between tests, never stop). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
msw 2.13 shipped a "network source architecture" refactor (mswjs/msw#2650) that altered the worker lifecycle. Our fixture called worker.start() before each test and worker.stop() after, which on 2.13 creates a race: the next test's start() can't take over before requests are made, so they bypass the worker and hit Vite directly — surfacing as "Failed to fetch" and 20s timeouts on every test that makes a request. The upstream fix is to simply not call worker.stop(). This matches the official vitest-browser-mode recipe (https://mswjs.io/docs/recipes/vitest-browser-mode). Tracked upstream at mswjs/msw#2706. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…updates (#225) * chore(deps): Bump the minor-updates group across 1 directory with 21 updates Bumps the minor-updates group with 21 updates in the / directory: | Package | From | To | | --- | --- | --- | | [@sentry/react](https://github.com/getsentry/sentry-javascript) | `10.46.0` | `10.48.0` | | [@sentry/vite-plugin](https://github.com/getsentry/sentry-javascript-bundler-plugins) | `5.1.1` | `5.2.0` | | [@tanstack/react-query](https://github.com/TanStack/query/tree/HEAD/packages/react-query) | `5.95.2` | `5.99.0` | | [@tanstack/react-query-persist-client](https://github.com/TanStack/query/tree/HEAD/packages/react-query-persist-client) | `5.95.2` | `5.99.0` | | [@tanstack/react-router](https://github.com/TanStack/router/tree/HEAD/packages/react-router) | `1.168.8` | `1.168.21` | | [react](https://github.com/facebook/react/tree/HEAD/packages/react) | `19.2.4` | `19.2.5` | | [react-dom](https://github.com/facebook/react/tree/HEAD/packages/react-dom) | `19.2.4` | `19.2.5` | | [@rolldown/plugin-babel](https://github.com/rolldown/plugins/tree/HEAD/packages/babel) | `0.2.2` | `0.2.3` | | [@tanstack/eslint-plugin-query](https://github.com/TanStack/query/tree/HEAD/packages/eslint-plugin-query) | `5.97.0` | `5.99.0` | | [@tanstack/react-query-devtools](https://github.com/TanStack/query/tree/HEAD/packages/react-query-devtools) | `5.95.2` | `5.99.0` | | [@tanstack/react-router-devtools](https://github.com/TanStack/router/tree/HEAD/packages/react-router-devtools) | `1.166.11` | `1.166.13` | | [@tanstack/router-plugin](https://github.com/TanStack/router/tree/HEAD/packages/router-plugin) | `1.167.9` | `1.167.22` | | [@types/node](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/node) | `24.12.0` | `24.12.2` | | [@vitest/browser-playwright](https://github.com/vitest-dev/vitest/tree/HEAD/packages/browser-playwright) | `4.1.2` | `4.1.4` | | [@vitest/coverage-v8](https://github.com/vitest-dev/vitest/tree/HEAD/packages/coverage-v8) | `4.1.2` | `4.1.4` | | [msw](https://github.com/mswjs/msw) | `2.12.14` | `2.13.3` | | [oxfmt](https://github.com/oxc-project/oxc/tree/HEAD/npm/oxfmt) | `0.42.0` | `0.45.0` | | [oxlint-tsgolint](https://github.com/oxc-project/tsgolint) | `0.20.0` | `0.21.0` | | [vite](https://github.com/vitejs/vite/tree/HEAD/packages/vite) | `8.0.5` | `8.0.8` | | [vitest](https://github.com/vitest-dev/vitest/tree/HEAD/packages/vitest) | `4.1.2` | `4.1.4` | | [vitest-browser-react](https://github.com/vitest-community/vitest-browser-react) | `2.1.0` | `2.2.0` | Updates `@sentry/react` from 10.46.0 to 10.48.0 - [Release notes](https://github.com/getsentry/sentry-javascript/releases) - [Changelog](https://github.com/getsentry/sentry-javascript/blob/develop/CHANGELOG.md) - [Commits](getsentry/sentry-javascript@10.46.0...10.48.0) Updates `@sentry/vite-plugin` from 5.1.1 to 5.2.0 - [Release notes](https://github.com/getsentry/sentry-javascript-bundler-plugins/releases) - [Changelog](https://github.com/getsentry/sentry-javascript-bundler-plugins/blob/main/CHANGELOG.md) - [Commits](getsentry/sentry-javascript-bundler-plugins@5.1.1...5.2.0) Updates `@tanstack/react-query` from 5.95.2 to 5.99.0 - [Release notes](https://github.com/TanStack/query/releases) - [Changelog](https://github.com/TanStack/query/blob/main/packages/react-query/CHANGELOG.md) - [Commits](https://github.com/TanStack/query/commits/@tanstack/react-query@5.99.0/packages/react-query) Updates `@tanstack/react-query-persist-client` from 5.95.2 to 5.99.0 - [Release notes](https://github.com/TanStack/query/releases) - [Changelog](https://github.com/TanStack/query/blob/main/packages/react-query-persist-client/CHANGELOG.md) - [Commits](https://github.com/TanStack/query/commits/@tanstack/react-query-persist-client@5.99.0/packages/react-query-persist-client) Updates `@tanstack/react-router` from 1.168.8 to 1.168.21 - [Release notes](https://github.com/TanStack/router/releases) - [Changelog](https://github.com/TanStack/router/blob/main/packages/react-router/CHANGELOG.md) - [Commits](https://github.com/TanStack/router/commits/@tanstack/react-router@1.168.21/packages/react-router) Updates `react` from 19.2.4 to 19.2.5 - [Release notes](https://github.com/facebook/react/releases) - [Changelog](https://github.com/facebook/react/blob/main/CHANGELOG.md) - [Commits](https://github.com/facebook/react/commits/v19.2.5/packages/react) Updates `react-dom` from 19.2.4 to 19.2.5 - [Release notes](https://github.com/facebook/react/releases) - [Changelog](https://github.com/facebook/react/blob/main/CHANGELOG.md) - [Commits](https://github.com/facebook/react/commits/v19.2.5/packages/react-dom) Updates `@rolldown/plugin-babel` from 0.2.2 to 0.2.3 - [Release notes](https://github.com/rolldown/plugins/releases) - [Changelog](https://github.com/rolldown/plugins/blob/main/packages/babel/CHANGELOG.md) - [Commits](https://github.com/rolldown/plugins/commits/plugin-babel@0.2.3/packages/babel) Updates `@tanstack/eslint-plugin-query` from 5.97.0 to 5.99.0 - [Release notes](https://github.com/TanStack/query/releases) - [Changelog](https://github.com/TanStack/query/blob/main/packages/eslint-plugin-query/CHANGELOG.md) - [Commits](https://github.com/TanStack/query/commits/@tanstack/eslint-plugin-query@5.99.0/packages/eslint-plugin-query) Updates `@tanstack/react-query-devtools` from 5.95.2 to 5.99.0 - [Release notes](https://github.com/TanStack/query/releases) - [Changelog](https://github.com/TanStack/query/blob/main/packages/react-query-devtools/CHANGELOG.md) - [Commits](https://github.com/TanStack/query/commits/@tanstack/react-query-devtools@5.99.0/packages/react-query-devtools) Updates `@tanstack/react-router-devtools` from 1.166.11 to 1.166.13 - [Release notes](https://github.com/TanStack/router/releases) - [Changelog](https://github.com/TanStack/router/blob/main/packages/react-router-devtools/CHANGELOG.md) - [Commits](https://github.com/TanStack/router/commits/@tanstack/react-router-devtools@1.166.13/packages/react-router-devtools) Updates `@tanstack/router-plugin` from 1.167.9 to 1.167.22 - [Release notes](https://github.com/TanStack/router/releases) - [Changelog](https://github.com/TanStack/router/blob/main/packages/router-plugin/CHANGELOG.md) - [Commits](https://github.com/TanStack/router/commits/@tanstack/router-plugin@1.167.22/packages/router-plugin) Updates `@types/node` from 24.12.0 to 24.12.2 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/node) Updates `@vitest/browser-playwright` from 4.1.2 to 4.1.4 - [Release notes](https://github.com/vitest-dev/vitest/releases) - [Commits](https://github.com/vitest-dev/vitest/commits/v4.1.4/packages/browser-playwright) Updates `@vitest/coverage-v8` from 4.1.2 to 4.1.4 - [Release notes](https://github.com/vitest-dev/vitest/releases) - [Commits](https://github.com/vitest-dev/vitest/commits/v4.1.4/packages/coverage-v8) Updates `msw` from 2.12.14 to 2.13.3 - [Release notes](https://github.com/mswjs/msw/releases) - [Changelog](https://github.com/mswjs/msw/blob/main/CHANGELOG.md) - [Commits](mswjs/msw@v2.12.14...v2.13.3) Updates `oxfmt` from 0.42.0 to 0.45.0 - [Release notes](https://github.com/oxc-project/oxc/releases) - [Changelog](https://github.com/oxc-project/oxc/blob/main/npm/oxfmt/CHANGELOG.md) - [Commits](https://github.com/oxc-project/oxc/commits/oxfmt_v0.45.0/npm/oxfmt) Updates `oxlint-tsgolint` from 0.20.0 to 0.21.0 - [Release notes](https://github.com/oxc-project/tsgolint/releases) - [Commits](oxc-project/tsgolint@v0.20.0...v0.21.0) Updates `vite` from 8.0.5 to 8.0.8 - [Release notes](https://github.com/vitejs/vite/releases) - [Changelog](https://github.com/vitejs/vite/blob/main/packages/vite/CHANGELOG.md) - [Commits](https://github.com/vitejs/vite/commits/v8.0.8/packages/vite) Updates `vitest` from 4.1.2 to 4.1.4 - [Release notes](https://github.com/vitest-dev/vitest/releases) - [Commits](https://github.com/vitest-dev/vitest/commits/v4.1.4/packages/vitest) Updates `vitest-browser-react` from 2.1.0 to 2.2.0 - [Release notes](https://github.com/vitest-community/vitest-browser-react/releases) - [Commits](vitest-community/vitest-browser-react@v2.1.0...v2.2.0) --- updated-dependencies: - dependency-name: "@sentry/react" dependency-version: 10.48.0 dependency-type: direct:production update-type: version-update:semver-minor dependency-group: minor-updates - dependency-name: "@sentry/vite-plugin" dependency-version: 5.2.0 dependency-type: direct:production update-type: version-update:semver-minor dependency-group: minor-updates - dependency-name: "@tanstack/react-query" dependency-version: 5.99.0 dependency-type: direct:production update-type: version-update:semver-minor dependency-group: minor-updates - dependency-name: "@tanstack/react-query-persist-client" dependency-version: 5.99.0 dependency-type: direct:production update-type: version-update:semver-minor dependency-group: minor-updates - dependency-name: "@tanstack/react-router" dependency-version: 1.168.21 dependency-type: direct:production update-type: version-update:semver-patch dependency-group: minor-updates - dependency-name: react dependency-version: 19.2.5 dependency-type: direct:production update-type: version-update:semver-patch dependency-group: minor-updates - dependency-name: react-dom dependency-version: 19.2.5 dependency-type: direct:production update-type: version-update:semver-patch dependency-group: minor-updates - dependency-name: "@rolldown/plugin-babel" dependency-version: 0.2.3 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: minor-updates - dependency-name: "@tanstack/eslint-plugin-query" dependency-version: 5.99.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: minor-updates - dependency-name: "@tanstack/react-query-devtools" dependency-version: 5.99.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: minor-updates - dependency-name: "@tanstack/react-router-devtools" dependency-version: 1.166.13 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: minor-updates - dependency-name: "@tanstack/router-plugin" dependency-version: 1.167.22 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: minor-updates - dependency-name: "@types/node" dependency-version: 24.12.2 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: minor-updates - dependency-name: "@vitest/browser-playwright" dependency-version: 4.1.4 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: minor-updates - dependency-name: "@vitest/coverage-v8" dependency-version: 4.1.4 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: minor-updates - dependency-name: msw dependency-version: 2.13.3 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: minor-updates - dependency-name: oxfmt dependency-version: 0.45.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: minor-updates - dependency-name: oxlint-tsgolint dependency-version: 0.21.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: minor-updates - dependency-name: vite dependency-version: 8.0.8 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: minor-updates - dependency-name: vitest dependency-version: 4.1.4 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: minor-updates - dependency-name: vitest-browser-react dependency-version: 2.2.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: minor-updates ... Signed-off-by: dependabot[bot] <support@github.com> * deps: pin msw to 2.12.14 to avoid 2.13 browser lifecycle regression msw 2.13 introduced a service-worker lifecycle change that breaks our vitest browser tests. Our per-test fixture calls worker.start()/stop() around each test; on 2.13 the stop → next start cycle leaves a window where requests bypass the worker and hit Vite directly, so the uuid lookup fails with "Failed to fetch" and dependent tests time out at 20s. This reproduces locally: upgrading to 2.13.3 fails ~13 tests; pinning back to 2.12.14 makes all 196 tests pass (~21s, matching baseline). Upstream bug: mswjs/msw#2706 Introduced by the 2.13.0 "network source architecture" refactor (mswjs/msw#2650). A follow-up PR will upgrade msw back to the latest and adjust the worker fixture to only start() once per test file (the recommended workaround: reset handlers between tests, never stop). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * chore: bump oxfmt pre-commit hook to v0.45.0 Align with the oxfmt bump in package.json so the pre-commit hook uses the same formatter version as CI and local dev. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> --------- Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Amund Eggen Svandal <aesvandal@gmail.com> Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
msw 2.13 shipped a "network source architecture" refactor (mswjs/msw#2650) that altered the worker lifecycle. Our fixture called worker.start() before each test and worker.stop() after, which on 2.13 creates a race: the next test's start() can't take over before requests are made, so they bypass the worker and hit Vite directly — surfacing as "Failed to fetch" and 20s timeouts on every test that makes a request. The upstream fix is to simply not call worker.stop(). This matches the official vitest-browser-mode recipe (https://mswjs.io/docs/recipes/vitest-browser-mode). Tracked upstream at mswjs/msw#2706. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
msw 2.13 shipped a "network source architecture" refactor (mswjs/msw#2650) that altered the worker lifecycle. Our fixture called worker.start() before each test and worker.stop() after, which on 2.13 creates a race: the next test's start() can't take over before requests are made, so they bypass the worker and hit Vite directly — surfacing as "Failed to fetch" and 20s timeouts on every test that makes a request. The upstream fix is to simply not call worker.stop(). This matches the official vitest-browser-mode recipe (https://mswjs.io/docs/recipes/vitest-browser-mode). Tracked upstream at mswjs/msw#2706. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
setupRemoteServer#1617rettime#2558Changes
SetupApibehaves by introducing: network frames, sources, controllers, anddefineNetwork.instanceofcheck. Instead, thekindproperty of the handler is used.Usage
The introduces APIs are meant to be used from the explicit
msw/futureexport path. The path itself isn't documented as the APIs are considered experimental until the next major release.Roadmap
HandlersKindand just inlined them in the handler classes.__kindprivate field from handler classes and madekindpublic. This is a safe change as nobody should be using these fields.handlersand the constructor argument for the handlers controller seems odd. Choose just one?handlersoption. After all,handlersare only needed as the input to the controller.setupServer. ThedefineNetworkAPI is rather low-level. ExportNetowrkOptionsto the user can just override some of them?createSetupServerCommonApior its alternative. That's a crucial part of extending the default behaviors.SetuApiisn't that difficult to implement by hand.onUnhandledFramecouldn't affect the request resolution because it's called afterframe.resolve()is finished.onUnhandledRequest: 'error'to ensure that the request is errored (not bypassed). There's currently a bug sinceonUnhandledFrameis called afterframe.resolve(), which always callspassthrough()before the unhandled frame callback.WebSocketNetworkFrame, that won't happen (exception in one handler will short-circuit the entire loop).server.boundary()to establish ASL boundaries for Node.js tests. TheNetworkApimust remain the same across environments. Environment-specific APIs must come from the environment entrypoints (msw/node) and applied explicitly.AsyncHandlersController.boundary()instead of theboundary()method insetup-server.ts.readyStatetoNetworkApiso implementers don't have to introduce it themselves (e.g. removeisStartedfromsetup-worker.tsand use anetwork.readyStatecheck)..enable()leaking from the network sources. Not awaitingnetwork.disable()inserver.stop()feels weird.enable/disableindefineNetwork.SetupWorkerApiwas exported as a class before, now it's only a type. Re-implement that class similar to how we re-implementSetupServerApifor backwards compatibility.