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

Breaks child.type comparisons #54

Open
brandonkal opened this issue Aug 5, 2019 · 5 comments
Open

Breaks child.type comparisons #54

brandonkal opened this issue Aug 5, 2019 · 5 comments
Labels
bug Something isn't working Low priority

Comments

@brandonkal
Copy link

This will always return an empty array when activated:

const MenuItem = React.forwardRef((props, ref) => { return <div>Example</div> })
MenuItem.whyDidYouRender = true

let focusableChildrenTypes = [MenuItem]

let isFocusableChildType = (child): child is React.ReactElement =>
  focusableChildrenTypes.includes(child.type)
let getFocusableMenuChildren = (children) => {
  let focusable: any[] = []
  React.Children.forEach(children, (child) => {
    console.log('Checking focusable', child.type === MenuItem)
    if (isFocusableChildType(child)) focusable.push(child)
  })
  return focusable
}

Is there a way to get this module to work with child.type comparisons? Thank you.

vzaidman added a commit that referenced this issue Sep 9, 2019
@vzaidman
Copy link
Collaborator

vzaidman commented Sep 9, 2019

Proved this happens with a failing test on branch children-types:
https://github.com/welldone-software/why-did-you-render/tree/children-types

@vzaidman
Copy link
Collaborator

vzaidman commented Sep 9, 2019

This is actually not surprising. Currently we track how a functional component changes by substituting it with another functional component that tracks props and renders the original functional component.

The type of any component that is rendered with "whyDidYouRender" enabled on it is indeed "WDYRFunctionalComponent" (instead of the expected "MenuItem" in this case).

A deep refactor is needed to deal with it- we need to somehow get access to every render of a Component's instance (React element) without substituting it with another one.

But- I consider this an edge case though because child.type is not documented (as far as I can tell) and no one should rely on it anyway, so it's a low priority for me. (Can be interesting to solve though)

@vzaidman
Copy link
Collaborator

vzaidman commented Sep 9, 2019

A workaround (not a very satisfying one, I know) is to use displayName instead of type like this:

child.displayName === MenuItem.displayName

@vzaidman vzaidman added bug Something isn't working Low priority labels Sep 9, 2019
@brandonkal
Copy link
Author

Perhaps the type getter could be monkey patched to return the type of the child if type is called on a WDYRFunctionalComponent wrapper.

vzaidman added a commit that referenced this issue Sep 13, 2019
@vzaidman
Copy link
Collaborator

vzaidman commented Oct 4, 2019

Perhaps the type getter could be monkey patched to return the type of the child if type is called on a WDYRFunctionalComponent wrapper.

I tried it. This can't be done. the type getter is strictly read only :(

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working Low priority
Projects
None yet
Development

No branches or pull requests

2 participants