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

properly handling invalid scryRenderedDOMComponentsWithClass args #6529

Merged
merged 1 commit into from
Apr 22, 2016
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 9 additions & 3 deletions src/test/ReactTestUtils.js
Original file line number Diff line number Diff line change
Expand Up @@ -178,9 +178,6 @@ var ReactTestUtils = {
* @return {array} an array of all the matches.
*/
scryRenderedDOMComponentsWithClass: function(root, classNames) {
if (!Array.isArray(classNames)) {
classNames = classNames.split(/\s+/);
}
return ReactTestUtils.findAllInRenderedTree(root, function(inst) {

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

probably

+          invariant(
+            classNames !== undefined,
+            'TestUtils.scryRenderedDOMComponentsWithClass expects a ' +
+            'className as a second argument.'
+          );
           if (!Array.isArray(classNames)) {

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@sarbbottam I also thought about doing it that way. The reason that I did it the way I did was to make sure the errors were as useful and specific as possible. For example. If we were to do it the way that you're recommending, if someone makes a mistake and entered the className foo as the only argument. They will no longer receive the helpful error that states that foo is not an instance of a component but will be presented with this new error instead Invariant Violation: TestUtils.scryRenderedDOMComponentsWithClass expects a className a second argument , which, to me is more ambiguous and unclear of what part of their test they need to fix. I think the second (new) error is more helpful when it is only presented to the user after we have verified that the first argument is a valid instance of a component. That's my reasoning but I'm opening to updating the code to your implementation if that's the consensus. Thanks for the feedback!

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks @ipeters90 for the detailed explanation.

if someone makes a mistake and entered the className foo as the only argument

I guess then there should have been a check for root as well.

Copy link
Contributor Author

@ipetez ipetez Apr 18, 2016

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Inside of scryRenderedDOMComponentsWithClass, which takes in the root (instance of component) as the first argument, it calls ReactTestUtils.findAllInRenderedTree(root) which checks if root is a valid instance of a react component.

Reference: https://github.com/facebook/react/blob/master/src/test/ReactTestUtils.js#L168-171

So if someone calls scryRenderedDOMComponentsWithClass with no arguments or with an invalid root argument, it will throw an appropriate error (Invariant Violation: findAllInRenderedTree(...): instance must be a composite component). That seems sufficient to me. Do you think there's additional checks needed ? @sarbbottam

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Got it, thanks!!

if (ReactTestUtils.isDOMComponent(inst)) {
var className = inst.className;
Expand All @@ -189,6 +186,15 @@ var ReactTestUtils = {
className = inst.getAttribute('class') || '';
}
var classList = className.split(/\s+/);

if (!Array.isArray(classNames)) {
invariant(
classNames !== undefined,
'TestUtils.scryRenderedDOMComponentsWithClass expects a ' +
'className as a second argument.'
);
classNames = classNames.split(/\s+/);
}
return classNames.every(function(name) {
return classList.indexOf(name) !== -1;
});
Expand Down