Test-Driven Development with react and Jest
Tags: tdd, react, jest
Published: 2021-02-21 16:19:22

**This will be a quick guide for automating the process of testing and formatting code, before committing.**

The stack we will be using are:
* Prettier (which auto-formats code so you can stay focused on substance over style).

* ESLint (which detects common coding mistakes). 
A linter is a program that uses a set of rules to detect code that, though
syntactically valid, is likely to contain mistakes.

* Husky, is a tool for managing Git hooks in JavaScript projects. Git hooks are scripts that Git runs before or after certain commands, such as commit or push.

---

>_The core tenet of the software development methodology known as test-driven development (TDD) is to write the tests first._

>_TDD changes the coding experience by giving you rapid feedback:
with your tests already in place, you can quickly find out what works and what doesn’t. That gives you the freedom to experiment with different approaches._

---

# **Tests in react**

If you start your react project with Create React App. It is ready to use and ships with Jest!

With Jest as your test framework, you’ll be able to create a lightning-fast feedback loop.

---

###Creating tests: 

- First step is to create a file and a test file:
![image](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/uooe35yw3jsottusex4u.png)
 
What a basic test consists of:

❶ describe() declares a test suite, which is a grouping of tests. Its first argument
is a name, and the second is a function containing one or more tests.

❷ it() declares a test. Its first argument is a name, and the second is a function with the actual test code.

❸ expect() creates an assertion. It takes a single argument, typically a value
generated by the code being tested, and returns an object that exposes a set of matcher functions.
+
toBe() is a matcher that performs a strict equality test between the value being tested (the expect() argument) and the expected value (its own argument).
**or**
The toEqual() assertion method, which checks for deep object equality

Implemented like so:
```js
//Palindromes.test.js
import Palindromes from "./Palindromes";
describe("palindromes()", () => {
	it("correctly identifies one-word palindromes", () => {
		expect(Palindromes("madam")).toEqual(["madam"]);
	});
});
```

```js
//Palindromes.js
export default function Palindromes(str) {
    return [str];
}
```
To run the test, write following command-line in the command prompt.
```npm run test```

---

## Let's get down to the nitty-gritty stuff


**Prettier**
 commands for code formatting packages
* `npm i -D prettier`
* `npm i -D eslint-config-prettier`

**Files needed to be created**
.prettierignore -> Here we will put files that it should ignore:
   * node_modules
   * coverage
   * build
   * .vscode

.prettierrc.json -> the rules for our formatting
 ```json
{
	"trailingComma": "es5",
	"tabWidth": 2,
	"semi": true,
	"singleQuote": false,
	"useTabs": true,
	"jsxSingleQuote": false,
	"bracketSpacing": true,
	"jsxBracketSameLine": true,
	"arrowParens": "always",
	"htmlWhitespaceSensitivity": "css",
	"printWidth": 120,
	"quoteProps": "consistent"
}
```


**Pre-commit hook**

* Running a command before comitting

**Pre-commit hooks is used for**

* Running prettier
* Running tests

install a pre-commit hook for prettier, husky and lint-staged
* `npx mrm lint-staged` 
* add "prettier": "prettier --write ." to scripts or use "prettier --write src/" to only format files in the src folder etc.

By running `npm run prettier`, we can now manually prettify the files.

install husky folder
* `npx husky install`

install a pre-commit hook for our tests, 
* `npx husky add .husky/pre-commit "npm test"` 
* add npm run prettier to the pre-commit file

**Install cross-env**
`npm i -D cross-env`

in package.json: `"test": "cross-env CI=true react-scripts test"`

**That's it!**

Now we have successfully made an automated testing and formatting workspace, which will run every time we try and commit
(it will only commit if it passes the test). 
This will eliminate unreadable code and committing code with bugs.

---
I will leave you with a quote from Trevor Burnham

>_In the long term, the habit of putting tests first helps to form a healthy mindset for problem solving, one in which failing code evokes curiosity instead of despair._

---

 **To learn more go visit:**

[Husky Webpage](https://typicode.github.io/husky/#/)

[Prettier Webpage](https://prettier.io/)

[Jest Webpage](https://jestjs.io/)

[TDD Book by Trevor Burnham](https://www.amazon.com/Test-Driven-React-Problems-Quickly-Confidence/dp/1680506463/ref=sr_1_2?dchild=1&keywords=test+driven+react&qid=1613924310&sr=8-2)