---
title: Known issues · Cloudflare Workers docs
description: Explore the known issues associated with the Workers Vitest integration.
lastUpdated: 2025-04-16T21:02:18.000Z
chatbotDeprioritize: false
source_url:
  html: https://developers.cloudflare.com/workers/testing/vitest-integration/known-issues/
  md: https://developers.cloudflare.com/workers/testing/vitest-integration/known-issues/index.md
---

The Workers Vitest pool is currently in open beta. The following are issues Cloudflare is aware of and fixing:

### Coverage

Native code coverage via [V8](https://v8.dev/blog/javascript-code-coverage) is not supported. You must use instrumented code coverage via [Istanbul](https://istanbul.js.org/) instead. Refer to the [Vitest Coverage documentation](https://vitest.dev/guide/coverage) for setup instructions.

### Fake timers

Vitest's [fake timers](https://vitest.dev/guide/mocking.html#timers) do not apply to KV, R2 and cache simulators. For example, you cannot expire a KV key by advancing fake time.

### Dynamic `import()` statements with `SELF` and Durable Objects

Dynamic `import()` statements do not work inside `export default { ... }` handlers when writing integration tests with `SELF`, or inside Durable Object event handlers. You must import and call your handlers directly, or use static `import` statements in the global scope.

### Durable Object alarms

Durable Object alarms are not reset between test runs and do not respect isolated storage. Ensure you delete or run all alarms with [`runDurableObjectAlarm()`](https://developers.cloudflare.com/workers/testing/vitest-integration/test-apis/#durable-objects) scheduled in each test before finishing the test.

### WebSockets

Using WebSockets with Durable Objects with the [`isolatedStorage`](https://developers.cloudflare.com/workers/testing/vitest-integration/isolation-and-concurrency) flag turned on is not supported. You must set `isolatedStorage: false` in your `vitest.config.ts` file.

### Isolated storage

When the `isolatedStorage` flag is enabled (the default), the test runner will undo any writes to the storage at the end of the test as detailed in the [isolation and concurrency documentation](https://developers.cloudflare.com/workers/testing/vitest-integration/isolation-and-concurrency/). However, Cloudflare recommends that you consider the following actions to avoid any common issues:

#### Await all storage operations

Always `await` all `Promise`s that read or write to storage services.

```ts
// Example: Seed data
beforeAll(async () => {
  await env.KV.put('message', 'test message');
  await env.R2.put('file', 'hello-world');
});
```

#### Explicitly signal resource disposal

When calling RPC methods of a Service Worker or Durable Object that return non-primitive values (such as objects or classes extending `RpcTarget`), use the `using` keyword to explicitly signal when resources can be disposed of. See [this example test](https://github.com/cloudflare/workers-sdk/tree/main/fixtures/vitest-pool-workers-examples/rpc/test/unit.test.ts#L155) and refer to [explicit-resource-management](https://developers.cloudflare.com/workers/runtime-apis/rpc/lifecycle#explicit-resource-management) for more details.

```ts
using result = await stub.getCounter();
```

#### Consume response bodies

When making requests via `fetch` or `R2.get()`, consume the entire response body, even if you are not asserting its content. For example:

```ts
test('check if file exists', async () => {
  await env.R2.put('file', 'hello-world');
  const response = await env.R2.get('file');


  expect(response).not.toBe(null);
  // Consume the response body even if you are not asserting it
  await response.text()
});
```

### Module resolution

If you encounter module resolution issues such as: `Error: Cannot use require() to import an ES Module` or `Error: No such module`, you can bundle these dependencies using the [deps.optimizer](https://vitest.dev/config/#deps-optimizer) option:

```tsx
import { defineWorkersConfig } from "@cloudflare/vitest-pool-workers/config";


export default defineWorkersConfig({
  test: {
    deps: {
      optimizer: {
        ssr: {
          enabled: true,
          include: ["your-package-name"],
        },
      },
    },
    poolOptions: {
      workers: {
        // ...
      },
    },
  },
});
```

You can find an example in the [Recipes](https://developers.cloudflare.com/workers/testing/vitest-integration/recipes) page.

### Importing modules from global setup file

Although Vitest is set up to resolve packages for the `workerd` runtime, it runs your global setup file in the Node.js environment. This can cause issues when importing packages like [Postgres.js](https://github.com/cloudflare/workers-sdk/issues/6465), which exports a non-Node version for `workerd`. To work around this, you can create a wrapper that uses Vite's SSR module loader to import the global setup file under the correct conditions. Then, adjust your Vitest configuration to point to this wrapper. For example:

```ts
// File: global-setup-wrapper.ts
import { createServer } from "vite"


// Import the actual global setup file with the correct setup
const mod = await viteImport("./global-setup.ts")


export default mod.default;


// Helper to import the file with default node setup
async function viteImport(file: string) {
  const server = await createServer({
    root: import.meta.dirname,
    configFile: false,
    server: { middlewareMode: true, hmr: false, watch: null, ws: false },
    optimizeDeps: { noDiscovery: true },
    clearScreen: false,
  });
  const mod = await server.ssrLoadModule(file);
  await server.close();
  return mod;
}
```

```ts
// File: vitest.config.ts
import { defineWorkersConfig } from "@cloudflare/vitest-pool-workers/config";


export default defineWorkersConfig({
  test: {
    // Replace the globalSetup with the wrapper file
    globalSetup: ["./global-setup-wrapper.ts"],
    poolOptions: {
      workers: {
        // ...
      },
    },
  },
});
```
