Playwright · Reliable end-to-end tests

How do you mock an API response in a Playwright test?

Mediummockingnetworktest dataUpdated Oct 2026
Quiz this track

Short answer

Intercept the request with page.route and call route.fulfill with a status, content type and body. Mock at the network boundary so the UI runs unchanged.

Mocking a response is useful for error states, empty states, slow responses and third-party services you do not control. Because the mock sits at the network layer, the application code still runs, so the test verifies how the UI reacts rather than bypassing it.

ts
await page.route("**/api/cart", async (route) => {
  await route.fulfill({
    status: 200,
    contentType: "application/json",
    body: JSON.stringify({ items: [], total: 0 }),
  });
});

await page.goto("/cart");
await expect(page.getByText("Your cart is empty")).toBeVisible();
The UI renders its real empty state from the mocked response.

Mocking well

  • Mock the smallest set of endpoints needed for the scenario
  • Return realistic shapes, because a too-permissive mock hides contract bugs
  • Mock error paths explicitly instead of relying on the backend to fail
  • Keep the mock setup close to the test that needs it
  • Use a shared helper only when many tests need the same contract
ts
let payload: unknown;

await page.route("**/api/cart", async (route) => {
  payload = route.request().postDataJSON();
  await route.fulfill({
    status: 201,
    contentType: "application/json",
    body: "{}",
  });
});

await page.getByRole("button", { name: "Add to cart" }).click();
expect(payload).toMatchObject({ quantity: 2 });
Capture the outgoing request so the test can assert what the UI sent.

If a test mocks every endpoint, it stops being an integration test and becomes a test of the mock. Prefer the real backend for the main happy path, and reserve mocks for slow, unreliable or hard-to-trigger conditions such as a 500 or a timeout.

Mocks must match the real contract closely enough to catch regressions. When the API shape changes, update the shared mock fixtures and consider a contract test so the drift is caught.

Follow-ups you should expect

Interviewers use these to check whether the first answer was understanding or memorisation.

  1. 1When should you mock instead of using the real API?
  2. 2How do you assert on the request body?
  3. 3What is the risk of mocking every endpoint?
  4. 4How do you simulate a slow or failed response?

Say it in the interview

I intercept the endpoint with the route API and return a controlled response with fulfill. The application still runs, so I can verify how it renders an empty state or an error. I keep mocks narrow and realistic, and I capture the outgoing payload when I need to assert what the UI sent. For the main happy path I usually prefer the real backend, because a suite that mocks everything stops testing integration.

Use this as a model, not a script. Saying it in your own words is what makes it survive follow-up pressure.

Related questions

Reading is step one

Now say it out loud.

Understanding an answer and delivering it under pressure are different skills. Rehearse this topic in a live Playwright mock interview and get scored feedback on depth, clarity and confidence.