-
Notifications
You must be signed in to change notification settings - Fork 4.2k
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
Context System: Don't explicitly set undefined
value to children
#42686
Conversation
Size Change: +110 B (0%) Total Size: 1.26 MB
ℹ️ View Unchanged
|
|
||
render( | ||
<ContextSystemProvider> | ||
<ConnectedComponent /> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This test (passing on trunk
) establishes how implicitly undefined children
were not a problem as long as the underlying component did not do a cloneElement()
.
expect( screen.getByText( 'Pass through' ) ).toBeInTheDocument(); | ||
} ); | ||
|
||
test( 'should not accept children via `context`', () => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I actually don't know if this is intentional/desirable, but it is the existing behavior in trunk
.
// Setting an `undefined` explicitly can cause unintended overwrites | ||
// when a `cloneElement()` is involved. | ||
if ( rendered !== undefined ) { | ||
// @ts-ignore | ||
finalComponentProps.children = rendered; | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In the very unlikely case that someone wants to explicitly wipe out the inherent children of a component using cloneElement()
, they can still pass children=null
.
For normal components that don't involve cloneElement()
, children
overrides will be (and have been) ignored anyway.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you for the sleuthing and the great explanation in this PR, Lena!
Code changes LGTM 🚀 and it's great to see new unit tests being added!
Fixes #42380
What?
Prevents the Context System from explicitly setting an
undefined
value tochildren
.Why?
There was a problem where an
Icon
component could not be rendered via theas
prop.At first glance, this seemed like a general issue with context-connected components and the
as
prop. However, after going through a bunch of test cases, the problem was narrowed down to a relatively specific condition — when the underlying component uses acloneElement()
to create the output.There are some subtle differences in how
undefined
children are treated depending on how they are undefined. This is usually not a problem, except for when acloneElement()
call overrides the original element'schildren
withprops.children=undefined
:gutenberg/packages/icons/src/icon/index.js
Lines 17 to 23 in a256669
How?
Several test cases related to the
children
prop were added to the unit tests for the Context System. This helps us understand what the existing behavior is, and should give us sufficient confidence that the fix in this PR does not have unexpected side effects.Testing Instructions
In Storybook, try making a
<View as={ Icon }>
story like in the code snippet above. The icon SVG should render correctly after the fix in this PR.