Lloyd Banks
Lloyd Banks

Reputation: 36699

Jest - How To Test a Fetch() Call That Returns A Rejected Promise?

I have the following function that uses fetch() to make an API call:

export async function fetchCars(dealershipId) {
  return request('path/to/endpoint/' + dealershipId)
    .then((response) => {
      if (response.ok === false) {
        return Promise.reject();
      }
      return response.json();
    })
    .then((cars) => {
      return parseMyCars(cars);
    });
}

I want to test when the call fails (specifically when return Promise.reject() is returned). I have the following Jest test right now:

(fetch as jest.Mock).mockImplementation(() =>
    Promise.resolve({ ok: false })
);
const result = await fetchCars(1);
expect(request).toHaveBeenCalledWith('/path/to/endpoint/1');
expect(result).toEqual(Promise.reject());

but I get a Failed: undefined message when running the test. I've tried using:

(fetch as jest.Mock).mockRejectedValue(() =>
  Promise.resolve({ ok: false })
);

but get a similar Failed: [Function anonymous] message.

What's the proper way to test for the rejected promise here?

Upvotes: 4

Views: 8191

Answers (2)

lissettdm
lissettdm

Reputation: 13078

Your test is failing because it's throwing an exception. You need to catch that exception, there are many ways to do it, and using rejects helper is one of them:

it("should fail", async () => {
    (window.fetch as jest.Mock).mockResolvedValueOnce({
      ok: false,
    });
    await expect(fetchCars(1)).rejects.toEqual(/* error you are expecting*/);
});

Upvotes: 1

Steve
Steve

Reputation: 4995

There is a couple of ways to deal with this correctly. I think the issue is that you are awaiting your promise.

If you plan to use await then you must await the expect:

const result = fetchCars(1);
await expect(result).toEqual(Promise.reject());
// ✅ Correct setup

or you can just return the un-awaited promise:

const result = fetchCars(1);
return expect(result).toEqual(Promise.reject());
// ✅ Correct setup

If you don't return or await the expect, then you might notice you get a false positive:

const result = fetchCars(1);
expect(result).toEqual(Promise.reject());
// ❌ False positive!

I've created a codesandbox example showing you how to mock the fetch function and how to correctly set up the test including the incorrect ways. Have a play around with the Tests tab at the top right.

Upvotes: -1

Related Questions