Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Assertions on a wrapper inconsistently assert on children #191

Open
nigelrobbins3 opened this issue Jul 6, 2017 · 3 comments
Open

Assertions on a wrapper inconsistently assert on children #191

nigelrobbins3 opened this issue Jul 6, 2017 · 3 comments

Comments

@nigelrobbins3
Copy link

The behavior of to.have.prop is different than other assertions when used on a mounted wrapper. Take the following example.

class ButtonComponent extends React.Component {
  render() {
    return (
      <div id="foo">
        <span id="bar" />
      </div>
    );
  }
}

const wrapper = mount(<ButtonComponent baz="qux" />);
const spanWrapper = wrapper.find("span");

expect(spanWrapper).to.have.id("bar"); // passes
expect(spanWrapper).to.have.prop("id", "bar"); // passes

expect(wrapper).to.have.id("foo"); // passes
expect(wrapper).to.have.prop("id", "foo"); // fails
expect(wrapper).to.have.prop("baz", "qux"); // passes (even though it's on ButtonComponent)

Notice that the root wrapper treats to.have.id as though it is wrapping the div, but treats to.have.prop as though it is wrapping the ButtonComponent. This behavior is unexpected.

Why would I want to use prop("id", "foo") when I have id("foo")? I like to assert that my elements have a style prop, but I don't care what the values are (I find it very brittle to assert all the style properties and values).

expect(someWrapper).to.have.prop("style")

There's some special casing that is done to the root wrapper, because the output from wrapper.debug() is:

<ButtonComponent>
  <div id="foo">
    <span id="bar" />
  </div>
</ButtonComponent>

but wrapper.children().debug():

<span id="bar" />

Either enzyme does something special when it calls children(), or it does something special when it calls debug() on the root element. Regardless, the assertion expect(wrapper).to.have.prop("something") is checking the ButtonComponent element, not the div.

@ljharb brought up some points about this in this issue. In particular, asserting on what props were passed to a component is not meaningful because you pass them yourself when mounting. The current behavior is a bug; the assertion should be using the div.

@ljharb
Copy link
Member

ljharb commented Jul 7, 2017

Note tho that my comments describe how shallow behaves; it seems mount by necessity behaves differently.

@nigelrobbins3
Copy link
Author

Ok. Is it possible to improve that behavior? Or is enzyme not exposing the root node correctly?

The hack I usually use to get the properties of the root node is const root = wrapper.find("div").first(), but it requires knowing that the root element is a div

@ljharb
Copy link
Member

ljharb commented Jul 7, 2017

const root = wrapper.children().first()?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants