A guide to testing and formatting in react

Tags: react, testing, formatting, prehooks
Published: 2021-02-19 11:00:00

# A guide to testing and formatting in react

Here is a tutorial that explain how to implement

- Tests in react
- Pre-commit hooks for tests
- Prettier og rules for formatting in react
- Pre-commit hooks for prettier

Before we begin you need to find a code editor
For this tutorial i am using “visual studio code” but you decide which one you want to use

Start by creating a folder , but remember that the name has to be in lowercase and The folder has to be completely empty or react will not accept it.

Then you can open the terminal and enter the command ( npx create-react-app .)

Now you can run (npm start) to test that react is working
You should be at browser window popoing up with a page and the react logo.

## Installing packages

Now we need to install the rest of the npm packages with need for testing and formatting

we are going to be using

- prettier (formatting)
- eslint-config-prettier (prettier add on)
- husky (controls precommits)
- cross environment (connects scripts across platforms)

## Format packages

first we will use the command `npm i -D prettier` to install prettier and then the add on `npm i -D eslint-config-prettier`
that turns off all rules that are unnecessary or might conflict with Prettier

and that is our formatting done.

## Pre-commit packages

now for the pre-commit packages

we are going to install `npx mrm lint-staged` and this will install husky and lint-staged packages and update your package.json

after the first one we are going to install using this command `npx husky install`
this will help us make sure that our code is without errors and prevent that code from being uploaded and give you information to fix the issue so that you can commit working code.

for the last install we are going to write `npx husky add .husky/pre-commit "npm test"` and this will create a file in the folder .husky called pre-commit and adds the command "npm test"

## Installer cross-env

we need to install `npm i -D cross-env` and short what this does is end our test when is has finished and allows us to commit

after we manually add to our package.json these two commmads to scripts

- `"test": "cross-env CI=true react-scripts test"`
- `"prettier": "prettier --write ."`

and to the pre-commit file

add - `npm run prettier` and this runs prettier if the test is succesfull

## Setting up a test on a component

#### Here we see a simple component

```javascript
function Navbar(props) {
	return (
		<nav>
			<ul>
				<li>
					<a href="#">Home</a>
				</li>
				<li>
					<a href="#">About</a>
				</li>
				<li>
					<a href="#">Store</a>
				</li>
				<li>
					<a href="#">Contact</a>
				</li>
			</ul>
		</nav>
	);
}

export default Navbar;
```

now let's see how a test looks
here we are testing to see if the component `Navbar.js` is rendering "home" in the browser

```javascript
import { render, screen } from "@testing-library/react";
import Navbar from "./Navbar";

test("check to see if text home is rendered", () => {
	render(<Navbar />);
	const checker = screen.getByText(/Home/i);
	expect(checker).toBeInTheDocument();
});
```

so when we run `npm test` we will get

```
PASS src/Navbar.test.js
  ✓ check to see if text home is rendered (33 ms)

Test Suites: 1 passed, 1 total
Tests:       1 passed, 1 total
Snapshots:   0 total
Time:        1.878 s, estimated 2 s
Ran all test suites.
```

here we see the test is passed

if the code were to fail it would look like this

```
FAIL src/Navbar.test.js
  ✕ check to see if text home is rendered (34 ms)

  ● check to see if text home is rendered

    TestingLibraryElementError: Unable to find an element with the text: /Homie/i. This could be because the text is broken up by multiple elements. In this case, you can provide a function for your text matcher to make your matcher more flexible.

    <body>
      <div>
        <nav>
          <ul>
            <li>
              <a
                href="#"
              >
                Home
              </a>
            </li>
            <li>
              <a
                href="#"
              >
                About
              </a>
            </li>
            <li>
              <a
                href="#"
              >
                Store
              </a>
            </li>
            <li>
              <a
                href="#"
              >
                Contact
              </a>
            </li>
          </ul>
        </nav>
      </div>
    </body>

       5 | test('check to see if text home is rendered', () => {
       6 |   render(<Navbar />);
    >  7 |   const checker = screen.getByText(/Homie/i);
         |                          ^
       8 |   expect(checker).toBeInTheDocument();
       9 | });
      10 |

      at Object.getElementError (node_modules/@testing-library/dom/dist/config.js:37:19)
      at node_modules/@testing-library/dom/dist/query-helpers.js:90:38
      at node_modules/@testing-library/dom/dist/query-helpers.js:62:17
      at getByText (node_modules/@testing-library/dom/dist/query-helpers.js:111:19)
      at Object.<anonymous> (src/Navbar.test.js:7:26)

Test Suites: 1 failed, 1 total
Tests:       1 failed, 1 total
Snapshots:   0 total
Time:        1.952 s, estimated 2 s
Ran all test suites.
npm ERR! Test failed.  See above for more details.
```

It tells us what kind of error we are dealing with and where to locate it
so we can fix it.

in this example we changed home to homie so the test will fail because it can't find `home`
and when we correct the error our test will pass.

now lets have a look at prettier and what that does for our code

this example of a code that is hard to read because of poor formatting

```
function Navbar(props) {
	return (
	<nav>
		<ul>
				<li>
		<a href="#">Home</a>
				</li>
				<li>
	<a href="#">About</a>
			</li>
				<li>
					<a href="#">Store</a>
		</li>
		<li>
					<a href="#">Contact</a>
		</li>
		</ul>
		</nav>
	);
}

export default Navbar;
```

but because we use prettier wich run with our `git commit -m "message"`
so it will fix our poor formatting for us and make it look like this and we get nice readable code. 

```
function Navbar(props) {
	return (
		<nav>
			<ul>
				<li>
					<a href="#">Home</a>
				</li>
				<li>
					<a href="#">About</a>
				</li>
				<li>
					<a href="#">Store</a>
				</li>
				<li>
					<a href="#">Contact</a>
				</li>
			</ul>
		</nav>
	);
}

export default Navbar;

```

but if the test doesn't pass you can't commit and prettier will not run.