This is a Next.js project bootstrapped with create-next-app.
First install dependencies and then run the development server:
npm install
# then
npm run devThe project includes an API mock for the /api/sign-in end-point.
The code in this repository was developed using Node v12.19.0.
Open http://localhost:3000 with your browser to see the login form demo.
npm run test
# then
npm run test:watchThe project doesn't have to be running to run the tests, they're independent. The tests use MSW for API mocking.
Test runner Jest.
Auxiliary testing library for React React Testing Library.
DOM assertions library jest-dom.
User events simulation library user-event.
API mocking with Mocking Service Worker.
Testing Implementation Details
Here's a process for how to know what to test. Following this process helps you have the right mindset when testing and you will naturally avoid implementation details:
- What part of your untested codebase would be really bad if it broke? (The checkout process)
- Try to narrow it down to a unit or a few units of code (When clicking the "checkout" button a request with the cart items is sent to /checkout)
- Look at that code and consider who the "users" are (The developer rendering the checkout form, the end user clicking on the button)
- Write down a list of instructions for that user to manually test that code to make sure it's not broken. (render the form with some fake data in the cart, click the checkout button, ensure the mocked /checkout API was called with the right data, respond with a fake successful response, make sure the success message is displayed).
- Turn that list of instructions into an automated test.
Static vs Unit vs Integration vs E2E Testing for Frontend Apps
Fix the "not wrapped in act(...)" warning
Write tests. Not too many. Mostly integration.
Common mistakes with React Testing Library
To keep snapshots short, prefer toMatchInlineSnapshot over toMatchSnapshot.
it("renders its heading centered (snapshot)", () => {
render(<LoginForm />);
const heading = screen.getByRole("heading", {
name: /Sign in to your account/i,
});
expect(heading).toMatchInlineSnapshot(`
<h2
class="mt-6 text-center text-3xl font-extrabold text-gray-900"
>
Sign in to your account
</h2>
`);
});When using toMatchInlineSnapshot you'll need to install prettier, which is used to format the argument passed to toMatchInlineSnapshot automatically for you.