2

For my React component I have the following:

const ArchiveButton = ({collection, onClick}) => {

    return (
        <span>
            { collection.archived &&
            <Button bsStyle="link" onClick={onClick}><i className="fa fa-rotate-left" />&nbsp;Unarchive</Button>
            }
            { !collection.archived &&
            <Button bsStyle="link" onClick={onClick}><i className="fa fa-archive" />&nbsp;Archive</Button>
            }
        </span>
    );
};

I'm attempting to test by passing in different values for collection.archived and I want to check for the existence of the text "Unarchive" vs "Archive". When I do a wrapper.find('Button') and try and check against .text() it is just <Button /> and the only way I've figured out how to test it is:

    const wrapper = shallow(<ArchiveButton onClick={onClick} {...props}/>);

    let button = wrapper.find('Button').prop('children');
    expect(button[1]).toMatch(/\sUnarchive/);

Seems a bit off though, not sure. Thanks!

Canta
  • 1,480
  • 1
  • 13
  • 26
kinabalu
  • 428
  • 1
  • 5
  • 10
  • Have you tried `props().children`? In that case, your expectation will be `expect(button[1].props().children).toEqual('Unarchive')` – Hardik Modha Mar 19 '17 at 18:16

1 Answers1

2

It's because you're using shallow rendering, so your nested Button component doesn't get rendered. As you've seen, you can access the nested component props to test the values you pass to it. If you prefer to have the button content rendered, use normal rendering instead.

Note that the nested Button is not a normal DOM element, which would be rendered anyway even if you use shallow rendering, but it's instead a component itself.

If you think about it, if you don't use shallow rendering in your case, you're not really unit-testing your component, as you're also asserting something about the Button component. If you use shallow rendering and access the props of the nested component, you're really just testing that your code is calling the Button component with the correct arguments, and you're not making any assumptions as how the Button component will render. This is normally what you want to do in a unit test.

fabio.sussetto
  • 6,964
  • 3
  • 25
  • 37
  • so I'd have to use mount() instead of shallow in that case? Is there anything wrong with using the nested component props? And is that the proper way to do so? – kinabalu Mar 19 '17 at 18:11
  • @kinabalu see my edit above, I don't think there's anything wrong with accessing the nested props, that's actually what you'd do in a "pure" unit test case. – fabio.sussetto Mar 19 '17 at 18:15