React Testing Librbary & Jest part 6 Big Project overview === ![](https://i.imgur.com/GYOSSUa.png) --- ###### tags: `React Testing Library`, `Jest`, `React` ## Testing in reality ![](https://i.imgur.com/F3UCI9g.png) ## Bug fix process ![](https://i.imgur.com/ldMBLkN.png) We can amend the flow by testing the result first (expect to be failed) then write test --> **Test-driven method**. > [TDD method](https://hackmd.io/@andreaFan321/B1Ytd-8Xh) ## Understanding the Data When we try to check where datas / props came from , we can use methods below: 1. Set a `console.log()` to print the data. 2. Set a `dbugger` and manually inspect the data. 3. Use React Developer Tools to view the props/state. 4. Watch network request log an inspect the API response. ## Testing files structure There're two ways of organizing test files like below. 1. Create a `__test__` folder and contains all the test files. 2. Place test file with components. ![](https://i.imgur.com/jBMUGCa.png) > For folder structure, read this article as a refrence - [Guidelines to improve your React folder structure](https://maxrozen.com/guidelines-improve-react-app-folder-structure) ## Analyzing Data... Before we start testing our app, we need to stop for a sec to make sure where the data comes from, meaning that we need to have a clear understanding of those components which might be written by someone else. ## Test cases ### 1. Check if component displays information. #### ✅Analyzing...where should we begin? Let's assume we've got a bug ticket saying that there's no primary language displayed next to forks. ![](https://i.imgur.com/idRyvo0.png) Where did the information come from? Let's open dev tools, and since it's an React app, we can use React dev tool to check the component. ![](https://i.imgur.com/UqmgiJu.png) When you hover these components, we can see there're highlight along with it. ![](https://i.imgur.com/NssXrea.png) Apparently the component we need to check is `<RepositorySummary />` #### ✅Take a look at the component The component received a props and the props has destructured. In order to make test work, we need to provide a prop as well. ![](https://i.imgur.com/3n7Luy3.png) Our goal is to add language next to forks, let's make sure if it has a property called language. Adding `console.log(repository)` within the component. Check console and expend it, see there's **language** inside of it. ![](https://i.imgur.com/bRv6Fuc.png) #### ✅Create a test file Since the test relates to ``<ReposirotySummary>``, we can put it inside of relevant folder. ![](https://i.imgur.com/CEZ6jNI.png) #### ✅ Writing test Create a mock repository as prop to the component and add language, ```javascript= // RepositorySumary.test.js import { render, screen } from '@testing-library/react'; import RepositoriesSummary from './RepositoriesSummary'; test('Displays information about the repo', () => { const repository = { language: 'Javascript', stargazers_count: 5, forks: 30, open_issues: 1, }; render(<RepositoriesSummary repository={repository} />); const language = screen.getByText('Javascript'); expect(language).toBeInTheDocument(); }); ``` #### ✅ Expected to be failed. Because we didn't add language inside our component, so the test result is expected. Let's add it in our component and the test result should be passed once we save the file. ![](https://i.imgur.com/RZl3O8J.png) #### ✅ Optimize code In the code above, we use `getByText('Javascript')` to check if text 'Javascript' is in the document, what if we want to check **stargazers_count** or **forks**, we surely can write like below: ```javascript= const language = screen.getByText(/Javascript/i); const stargazers_count = screen.getByText(5); const forks = screen.getByText(30); ... ``` What if we've got tones of properties to check? It's not effcient to create one by one, let's use loop to save time. ```javascript= test('Displays information about the repo', () => { const repository = { language: 'Javascript', stargazers_count: 5, forks: 30, open_issues: 1, }; render(<RepositoriesSummary repository={repository} />); for (let key in repository) { const value = repository[key]; // Using regular expression with every value const element = screen.getByText(new RegExp(value)); expect(element).toBeInTheDocument(); } ``` --- ### 2. Link to redirect use to the repository We've got another bug ticket said that when use click title of a repo, it can't redirct user to github. #### ✅Analyzing...where should we begin? ![](https://i.imgur.com/xtHpmdU.png) #### ✅Check component This component also received props, and we did add **link**, ummm...let's wrtie a test to check if it works as we expect. ![](https://i.imgur.com/aGA26an.png) #### ✅ Writing test ```javascript= import { render, screen } from '@testing-library/react'; import RepositoriesListItem from './RepositoriesListItem'; const renderComponent = () => { const repository = { full_name: 'facebook/react', language: 'Javascript', description: 'A js library', owner: 'facebook', name: 'react', html_url: 'https://github.com/facebook/react', }; render(<RepositoriesListItem repository={repository} />); }; test('shows a link to the github homepage for this repo', () => { renderComponent(); }); ``` #### ✅ Oh no...it's failed! Let's check error messages to see if there's any information that can help us to debug. What does this mean? ![](https://i.imgur.com/ksWu8pg.png) **Link** works only if there's **React Router context** avalible. ![](https://i.imgur.com/QV5dMtj.png) Inside our test, we did not provide router context, so we need to amend it. We've got 3 different options when it comes to router. - **BrowserRouter**: Stores current URL in the address bar. - **HashRoiter**: Stores current URL in the # part of the address bar. - **MemoryRouter**: Stores current URL in memory. (**Many blog posts recommend using this for testing purposes.**) #### ✅ Optimize it! ```javascript const renderComponent = () => { const repository = { full_name: 'facebook/react', language: 'Javascript', description: 'A js library', owner: 'facebook', name: 'react', html_url: 'https://github.com/facebook/react', }; render( <MemoryRouter> <RepositoriesListItem repository={repository} /> </MemoryRouter> ); }; test('shows a link to the github homepage for this repo', () => { renderComponent(); }); ```