What is Jest?
What is Jest?
Jest is a JavaScript testing framework originally created at Facebook (now Meta) alongside React, and today maintained by the community under the OpenJS Foundation. Despite its React roots, it is not limited to React — I use it just as happily for plain Node.js services, Express APIs, TypeScript libraries, Angular, and Vue projects.
What makes Jest the default choice is that it ships everything in one package: a test runner, an assertion library, mocking, code coverage, and snapshot testing. With Mocha you assemble those pieces yourself (Chai for assertions, Sinon for mocks, nyc for coverage); with Jest you install one dev dependency and start writing tests.
Getting Started
Installation
Jest is a Node-based runner. This means that the tests always run in a Node environment and not in a real browser. This lets us enable fast iteration speed and prevent flakiness.
First of all, create a new project in React, Express, or any other Node.js framework. I am going to use simple node js for this doc.
First of all, create directory and initialize npm:
mkdir jest-demo
cd jest-demo
- npm
- Yarn
- pnpm
- Bun
npm init -y
yarn init -y
pnpm init -y
bun init -y
Now, install Jest:
- npm
- Yarn
- pnpm
- Bun
npm install --save-dev jest
yarn add --dev jest
pnpm add --save-dev jest
bun add --dev jest
For TypeScript, you'll need to install ts-jest and @types/jest types, and set the ts-jest preset in your Jest config:
- npm
- Yarn
- pnpm
- Bun
npm install --save-dev ts-jest @types/jest
yarn add --dev ts-jest @types/jest
pnpm add --save-dev ts-jest @types/jest
bun add --dev ts-jest @types/jest
module.exports = {
preset: "ts-jest",
};
Test File Setup
Jest will look for test files with any of the following popular naming conventions:
- Files with
.js,.jsx,.tsor.tsxsuffix in__tests__folders. - Files with
.test.js,.test.jsx,.test.tsor.test.tsxsuffix. - Files with
.spec.js,.spec.jsx,.spec.tsor.spec.tsxsuffix.
The __tests__ folder name is special. Jest will consider files in __tests__ folders as tests, so you can store test files anywhere you want.
Writing Tests
To create a test case, call the test function inside a test file. Let's say we have a function that adds two numbers. We could test it like this:
// sum function
function sum(a, b) {
return a + b;
}
// test case for sum function
test("addition should return 4", () => {
const a = 2;
const b = 2;
expect(sum(a, b)).toBe(4);
});
This is your standard test call (it is an alias — it("adds two numbers", ...) behaves identically, pick one style and stay consistent). It receives two arguments:
- a string describing the behavior under test
- a callback that runs the test — the
expectcall checks whether the function produced the correct result
Running Tests
To run the test, we can use the npx jest command. This will run all the tests in the project.
npx jest
By default, Jest will look for files matching the above mentioned naming convention. To run a specific file, pass its name (or any part of the path — Jest treats it as a pattern):
npx jest math.test.js
To run a single test by name, use -t with part of the test description:
npx jest -t "addition"
In a real project, wire Jest into package.json so npm test works for everyone:
{
"scripts": {
"test": "jest"
}
}
Watch Mode
Jest can be run in watch mode. In this mode, Jest re-runs the tests affected by your changes every time you save a file — this is the mode I keep running while developing.
npx jest --watch
--watch requires a git repository, because it uses git to detect which files changed. Outside a repo, use --watchAll to re-run everything on every change.
Coverage
Coverage is a measure of how much of our code is executed by tests. Jest generates coverage reports out of the box:
npx jest --coverage
This prints a summary table and writes a detailed HTML report to the coverage folder. Treat the number as a guide, not a target — more on that in Testing Best Practices.
Assertions
Jest uses the expect function to make assertions. An assertion is a way to test the result of a function.
// sum function
function sum(a, b) {
return a + b;
}
// test case for sum function
test("addition should return 4", () => {
const a = 2;
const b = 2;
expect(sum(a, b)).toBe(4);
});
In the above example, we are using the toBe matcher to check whether the result of the sum function is 4.
Common Matchers
Jest has a lot of matchers that can be used to make assertions. Here are some of the most common matchers:
toBe()toEqual()not.toBe()toContain()toBeNull()toBeUndefined()toHaveLength()toThrow()toMatch()
toBe()
Checks if the result of a function is equal to the expected value using strict equality (===).
test("add function should correctly add two numbers", () => {
const result = add(2, 3);
expect(result).toBe(5);
});
toEqual()
Verifies deep equality between the result of a function and the expected value.
test("calculateTotal should return correct object", () => {
const cart = [10, 20, 30];
const result = calculateTotal(cart);
expect(result).toEqual({ total: 60 });
});
not.toBe()
Ensures that the result of a function is not strictly equal to the expected value.
test("subtract function should not return incorrect value", () => {
const result = subtract(10, 5);
expect(result).not.toBe(10);
});
toContain()
Verifies if an array, string, or iterable object contains the specified element or substring.
test("shopping cart should contain the added item", () => {
const cart = ["apple", "banana", "orange"];
const newItem = "pear";
cart.push(newItem);
expect(cart).toContain(newItem);
});
toBeNull()
Checks if the result of a function is null.
test("should return null", () => {
const result = null;
expect(result).toBeNull();
});
toBeUndefined()
Checks if the result of a function is undefined.
test("should return undefined", () => {
const result = undefined;
expect(result).toBeUndefined();
});
toHaveLength()
Checks if a string, array, or object has the specified length property.
test("string length should be equal to the specified length", () => {
const str = "Hello, World!";
expect(str).toHaveLength(13);
});
toThrow()
Ensures that a function throws an error when it is invoked.
test("divide function should throw an error when dividing by zero", () => {
const divideByZero = () => divide(10, 0);
expect(divideByZero).toThrow();
});
toMatch()
Verifies if a string matches the specified regular expression pattern.
test("email should match the regular expression pattern", () => {
const email = "test@example.com";
expect(email).toMatch(/^[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Z|a-z]{2,}$/);
});
These are the matchers I reach for daily. The full list lives in the Jest expect API reference, but a good rule of thumb: pick the most specific matcher available. expect(cart).toContain("pear") produces a far better failure message than expect(cart.includes("pear")).toBe(true) — the first tells you what the array actually contained, the second just says false is not true.
Next steps: Unit Testing covers test structure and setup/teardown, Mocking covers isolating dependencies, and Async Testing covers promises and timers.
Code
You can find the code for this doc from here