msw: Using a mocked request multiple times in a test suite fails

Environment

Name Version
msw 0.38.2
node 16.14.0
OS macOS 12.2.1

Request handlers


import { graphql } from "msw"
import { loader, action } from "~/routes/sign-in"

const createSignInHandler = ({ acceptRegistrations = true } = {}) => {
  return graphql.query("SignIn", (req, res, ctx) => {
    return res(ctx.data({ newUser: { acceptRegistrations } }))
  })
}

const server = setupServer(createSignInHandler())
beforeAll(() => server.listen())
afterEach(() => server.resetHandlers())
afterAll(() => server.close())


test("the loader returns data to determine if we are accepting registrations", async () => {
  const response = await loader({ request: new Request("/sign-in", { method: "GET" }), params: {}, context: {} })
  const data = await response.json()
  expect(data.acceptRegistrations).toBe(true)
})

Actual request


import { GraphQLClient,  gql as graphql } from "graphql-request"
import { SignInDocument, SignInQuery } from "~/graphql"

const client = new GraphQLClient(`${process.env.GRAPHQL_ENDPOINT}`, {})
const fetchQuery = async (query, variables, user, secret) => {
  try {
    const response = await client.request(query, variables || {}, getHeaders(user, secret))
   return response
  } catch (error: any) {
    return {}
  }
}

const loader = async () => {
  graphql`
    query SignIn {
      newUser {
        acceptRegistrations
      }
    }
  `
  const { newUser } = await fetchQuery<SignInQuery>(SignInDocument)
  return json({ acceptRegistrations: newUser?.acceptRegistrations || false })
}

Current behavior

If I have less than 4 tests in one suite the test pass. If I have four or more than I get the following error.

UnhandledPromiseRejection: This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). The promise rejected with the reason ""

I have ensure MSW is causing the error by hard coding the response and tested that the tests never fail (no matter how many tests are in the suite). If I have 3 tests or less the tests always pass, its only when four or more are added it fails.

I am using vitest (v0.5.9) with the following config:

/// <reference types="vitest" />
/// <reference types="vite/client" />

import { defineConfig } from "vite"
import react from "@vitejs/plugin-react"
import tsconfigPaths from "vite-tsconfig-paths"

export default defineConfig({
  plugins: [react(), tsconfigPaths()],
  test: {
    globals: true,
    environment: "jsdom",
    setupFiles: "./app/test-utils.ts",
    testTimeout: 20000
  }
})

Expected behavior

I can have as many tests as possible in a test suite.

About this issue

  • Original URL
  • State: closed
  • Created 2 years ago
  • Reactions: 1
  • Comments: 18 (5 by maintainers)

Most upvoted comments

Thanks for such a detailed investigation, @charklewis!

We need to look into what kind of request graphql-request makes when the test fails. We can do so by using DEBUG:

DEBUG=http* yarn test

In the case of test failure, there will be something to guide us.

It can still be an issue with how the constructed request gets handled in MSW.

@kettanaito I have done some more testing and it seems like the behaviour is a little haphazard. I have used the example repo I posted before, and running two duplicate tests. Below is a video of my re-running the test over and over, you can see it randomly failing and succeeding. As you’ll see in the code, its a really basic, no frills set up so I am unsure what is going wrong.

If there is any further experiments or troubleshooting you would like me to perform, please let me know. What I might try next is running the graphql query without it going through the loader to see if the loader from remix is causing the issue.

https://user-images.githubusercontent.com/11977093/158714784-b65f8be9-a122-48e3-855a-f6016bf00a30.mov

@kettanaito thanks for the reply, hope you had a great weekend! I’ll review my tests again to see if there is any async calls that are not being met. If I copy that test I mentioned above more than 3 times it’ll error, anything less it passes. I had a look at it appears the library I am using has no cache. This week I’ll create an example sandbox and comment it here.