facebook / react

The library for web and native user interfaces.
https://react.dev
MIT License
226.5k stars 46.21k forks source link

DevTools Components Hide components filter should hide the component it owns #29776

Open ricardo-reis-1970 opened 2 months ago

ricardo-reis-1970 commented 2 months ago

When I go to the Components tab of the React DevTools, I have an option to hide components in:

Settings > Components > Hide components where...

In this I can hide a component based on its name. The issue is that among many others I have a component called Period that has a ton of components underneath it because it uses React Datepicker. I add a rule like:

^ name matches Period

but all it hides is the entry for my component. I obviously expected to hide it together with all its descendants, but instead the very single line called Period vanishes from the tree, and now the tons of subcomponents (Datepicker, remember?) are all there as if hanging directly from the Period's parent component.

React version: 18.2.0 DevTools version: 5.2.0-1717ab0171

Steps To Reproduce

  1. create a React page with any component hierarchy with more than 2 levels
  2. in React DevTools > Components, go to Settings > Components > Hide components where...
  3. filter out a component by name
  4. now you'll see that the component that you filtered out disappeared, but its descendants are still all there, attached to the component's parent.

Link to code example:

My code is corporate and therefore cannot be shared. However, the description I gave and the steps to reproduce are quite unmistakable. This is not a circumstance bug on my code.

The current behavior

Currently, if I want to hide a component and all its descendants, I would need to add these one by one to the filters, which becomes highly impractical very soon.

Furthermore, in hiding components under the component I'm trying to hide, I might be hiding components elsewhere with the same name that I need not hide.

The expected behavior

I'm not sure what purpose this serves, but this is really not practical. There should at the very least be an option for physical filter and logical filter, where physical would be "every instance of this name" and logical would be "every instance of this name AND its descendants".

Other improvements would be selecting components to be collapsed by default (like filtering out, but with the option to see them).

Finally, not sure this is intended, but filtering is case insensitive. JavaScript is not.

eps1lon commented 2 months ago

Do you mean every child or only the children it explicitly renders e.g.

function Period({ children }) {
  //      vvv hide this component when hiding `Period`
  return <div>{children}</div>
  //           ^^^^^^^^ What about these components?
}
ricardo-reis-1970 commented 2 months ago

Hi Sebastian.

Thank you for the quick reply. Here's my Profile component: image

As you see, the component Period has a lot of stuff. All I can do is collapse it and get to this state: image

The issue is that when I filter out `Period, this is what I get: image

Now, all the descendants of PeriodDatePicker, NumberInput, etc. — are still in the tree, hanging directly from Profile and essentially making it even worse than before.

When I filter out one component, I don't expect a kind of a grep -v`` on that component's entries (what I called a *physical* filtering). I expect a *logical* filtering whereby I just hide the componentPeriodand all its children, essentially pruningPeriod` from the tree.

Collapsibles

Also (and for later), it would be really useful if I could also filter-collapse, as in saying that these components start collapsed in the tree view. This way, the collapsed components could always be open for inspection, but they would start "out of the way".

And here's how I thought this could be achieved: same way as you refresh the page and the tools highlight the last component yu highlighted, because of React::DevTools::lastSelection in sessionStorage, maybe something like that could also be implemented for this. Something like React::DevTools::collapsed, or React::DevTools::folded, whose value was a list of paths to fold.

Many thanks Ricardo

eps1lon commented 2 months ago

So

function Period({ children }) {
  //      vvv hide this if you filter out Period
  return <div>{children}</div>
  //           ^^^^^^^^ Hide this as well when you filter out Period
}

I don't think that's the right default here. Period could be a 3rd party component while children could be something you passed in. You wouldn't always want to filter children just because you filter Period. Maybe as an extra option. Would need so design work though to not overwhelm the UI.