Skip to content
tezvyn:

Jest Matchers: Asserting Values in Your Tests

Source: jestjs.ioEasyHow cards are made

Jest Matchers: Asserting Values in Your Tests

Jest matchers are assertion functions that check if a value meets a condition. You use them with expect() to verify function outputs, object properties, or promise states.

Why it exists

Writing tests requires a way to check that the values your code produces are correct. Without a structured way to make these checks, or "assertions," tests would be a messy collection of if/else statements, making it hard to see what failed and why.

The mental model

The expect function gives you access to a library of "matchers." A matcher is a function that performs a specific comparison. The pattern is always expect(value_from_your_code).matcher(expected_value). This reads like a sentence in English: "I expect the result of myFunction() to be true."

How it works

When you call expect(value), Jest returns an object containing all possible matcher functions. You chain one of these matchers, like .toBe() or .toEqual(), to perform the check. For example, .toBe() uses strict equality (===) for primitives, while .toEqual() recursively checks all properties of an object. Modifiers like .not can be chained before the matcher to invert the assertion. For asynchronous code, you can use .resolves or .rejects with async/await to test the outcome of a Promise.

When to use it

Use matchers in every Jest test you write, as they are the core mechanism for validating behavior. Common use cases include checking if a function returns a specific string with .toBe('some-string'), verifying an array contains an item with .toContain(item), ensuring an object has a certain shape with .toMatchObject({ key: value }), or testing that a function throws an error with .toThrow().

When not to use it

The primary footgun is not about when to avoid matchers, but how to use them correctly. The most common error is putting the expected value in expect() and the actual value in the matcher. For example, expect('grapefruit').toBe(bestLaCroixFlavor()) is wrong. While the test might pass, a failure will produce a confusing message like "Expected: 'pamplemousse', Received: 'grapefruit'". The correct form is expect(bestLaCroixFlavor()).toBe('grapefruit').

One canonical example

Imagine testing an async function fetchUser(id) that returns a user object. To test the success case, you would write: await expect(fetchUser(1)).resolves.toEqual({ id: 1, name: 'Leanne' });. This uses the .resolves modifier to handle the promise and .toEqual to deeply compare the resulting object. To test the failure case, you would write: await expect(fetchUser(99)).rejects.toThrow('User not found');. This asserts that the promise rejects and that the error message matches.

Interview question

Which of the following correctly uses a Jest matcher to assert that a function's output is 'hello'?

  • a.expect(myFunction(), 'hello').toBe()
  • b.expect('hello').toBe(myFunction())
  • c.expect(myFunction()).toBe('hello')Correct
  • d.myFunction().expect().toBe('hello')
Why?

The card specifies the pattern as expect(value_from_your_code).matcher(expected_value). Option C correctly places the actual value from myFunction() inside expect() and the expected value 'hello' inside the .toBe() matcher. Option B is a common error, swapping the actual and expected values, as highlighted in the 'WHEN NOT TO USE IT' section.

Just read this? Test yourself on what you have been reading.

Read the original → jestjs.io

You just looked this up. Could you explain it out loud?

That is the part interviews actually test. Tezvyn takes questions like this one and gives you what the interviewer is really checking, the answer that lands, and the mistake that ends the conversation, in the four minutes before your next meeting.

The iPhone app is on the way

We are building it. Until it lands, nothing here is held back from you: every interview card, your saved cards, streaks and the job board all work in Safari, plus hundreds of free practice quizzes of thirty questions each. Sign in and it all carries over to the app the day it arrives.

Want it as an icon? Tap Share at the bottom of Safari, then Add to Home Screen. It opens full screen and the cards you have read stay available offline.

Get it on Google PlayiPhone app coming soon

We are hiring for this. Every open role lists the topics its interview covers, so you can prepare for the real thing rather than guessing.

See open roles