Marnie A.
Marnie A.

Reputation: 73

Should I mount using beforeEach() and set props for each test or mount a specific component at the start of each test? (using Enzyme, Chai and Mocha)

I've recently starting programming. I'm on a team who is programming in React and is using Enzyme, Mocha and Chai for unit testing. See package versions below.

When testing a component where there are several use cases that require different prop values, should I use beforeEach() and then setProps() in each test, or should I do an explicit mount() (or shallow()) at the start of each test? Does it matter?

For example, I could use beforeEach() to mount without any props and then use setProps() in each test like this (using pseudocode):

describe('MyComponent', () => {

   beforeEach(... let component = mount(<MyComponent />) ...)

   it('tests use case 1', () => {
      // set prop A = 123
      component.setProps({A: 123})
      // assert some stuff
   })

   it('tests use case 2, () => {
      // set prop A = 456 and B = 'foo'
      component.setProps({A: 456})
      component.setProps({B: 'foo'})
      // assert some stuff
   })

})

or I could do a use-case specific mount at the start of each test, passing in props in the mount, like this:

describe('MyComponent', () => {

   it('tests use case 1', () => {
      ...mount(<MyComponent A=123 />)
      // assert some stuff
   })

   it('tests use case 2, () => {
      ...mount(<MyComponent A=456 B='foo' />)
      // assert some stuff
   })

})

What are the pros and cons of each method? Is there a best practice?

Packages

Upvotes: 2

Views: 2121

Answers (1)

skyboyer
skyboyer

Reputation: 23725

For class components there is componentDidMount and constructor while for functional components there is useEffect(..., []). All that things are called just once.

On the other side for approach #2 it's still needed to test props update in separate test case to ensure component handles that properly. Otherwise you may miss the case when say using the same component in different <Route> does not fetch data on navigation(that happen in componentDidMount only)

Say if you have

<Route path="/Album/:id/author" component={UserScreen} />
<Route path="/user/:id/" component={UserScreen} />

and if you can navigate directly from first to second it means React-Router will not re-create UserScreen but just update instance already rendered. So with approach #1 you would cover this case with tests automatically. While approach #2 will need you testing componentDidUpdate behavior explicitly.

I'm not sure what's better but want to highlight that difference may happen between testing flow and real-project-flow.

Upvotes: 0

Related Questions