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
fix(ivy): remove DOM nodes from their real parent vs saved parent #28455
Conversation
46153c9
to
a810dde
Compare
@@ -598,8 +598,16 @@ function nativeAppendOrInsertBefore( | |||
*/ | |||
export function nativeRemoveChild( | |||
renderer: Renderer3, parent: RElement, child: RNode, isHostElement?: boolean): void { | |||
isProceduralRenderer(renderer) ? renderer.removeChild(parent as RElement, child, isHostElement) : | |||
parent.removeChild(child); | |||
if (isProceduralRenderer(renderer)) { |
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.
If we do this logic here in nativeRemoveChild it will mean that we still execute all the logic to find a logical render parent and this is useless. I would rather modify the removeChild
function and there lookup a parent from the DOM, instead of executing const parentNative = getRenderParent(childTNode, currentView);
Then the null
check be in there as well and you wouldn't need to modify renderer
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.
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.
@jelbourn I believe @pkozlowski-opensource is actually talking about Ivy's version of removeChild
here (not the renderer):
https://github.com/angular/angular/blob/master/packages/core/src/render3/node_manipulation.ts#L696
I'd agree with him that we should update that function to remove the logic that searches the tree for the render parent manually.
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 totally misread Pawel's original comment; I hadn't seen that getRenderParent
function earlier.
In making the change to avoid calling that, I didn't want to move the "get parent node" bit into removeChild
because then nativeRemoveChild
would have the assumption that it's the right parent node baked into it. So, I instead changed removeChild
to removeNode
and made it just a pass-through to nativeRemoveChild
, which also now does not have parent
in its arguments.
Let me know what you think.
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 think that we should rather:
- modify the
removeChild
function (see my in-line comments); - have a
TestBed
test on top of / instead of renderer3 runtime test
Happy to help if needed but I would like to very much avoid the situation where we do both logical render parent lookup and lookup in the DOM.
a810dde
to
3adf1aa
Compare
3adf1aa
to
e8dffca
Compare
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.
Comments addressed, let me know what you think
@@ -598,8 +598,16 @@ function nativeAppendOrInsertBefore( | |||
*/ | |||
export function nativeRemoveChild( | |||
renderer: Renderer3, parent: RElement, child: RNode, isHostElement?: boolean): void { | |||
isProceduralRenderer(renderer) ? renderer.removeChild(parent as RElement, child, isHostElement) : | |||
parent.removeChild(child); | |||
if (isProceduralRenderer(renderer)) { |
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 totally misread Pawel's original comment; I hadn't seen that getRenderParent
function earlier.
In making the change to avoid calling that, I didn't want to move the "get parent node" bit into removeChild
because then nativeRemoveChild
would have the assumption that it's the right parent node baked into it. So, I instead changed removeChild
to removeNode
and made it just a pass-through to nativeRemoveChild
, which also now does not have parent
in its arguments.
Let me know what you think.
02eba52
to
b57c765
Compare
renderer.removeChild(renderParent, child, isHostElement); | ||
} | ||
} else { | ||
// We intentionally don't use the given parent node since it may no longer |
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.
There is no given parent node anymore, right?
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.
So the idea behind the native[...]()
functions in this file that those are here to basically abstract a renderer type being used. So far those functions didn't have any logic and I would love to keep it this way.
I would rather prefer that we keep nativeRemoveChild
"dumb" and move all the "logic" into the removeChild
function. I find this approach easier to follow and IMO the code is shorter / simpler (less checks / branching logic).
I've pushed a fixup commit I've pushed a fixup commit a529638 to your branch with the changes I'm describing above, please review. to your branch with the changes I'm describing above, please review.
if (parentNative) { | ||
nativeRemoveChild(currentView[RENDERER], parentNative, childEl); | ||
} | ||
export function removeNode(childTNode: TNode, childEl: RNode, currentView: LView): void { |
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.
childTNode
argument is not used here any more, remove
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.
Actually, I've pushed a fixup commit a529638 to your branch with the changes I'm describing above, please review.
So there's good news and bad news. 👍 The good news is that everyone that needs to sign a CLA (the pull request submitter and all commit authors) have done so. Everything is all good there. 😕 The bad news is that it appears that one or more commits were authored or co-authored by someone other than the pull request submitter. We need to confirm that all authors are ok with their commits being contributed to this project. Please have them confirm that here in the pull request. Note to project maintainer: This is a terminal state, meaning the |
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.
LGTM with the fixup commit but we can iterate more if @jelbourn has objections
@jelbourn I've pushed a fixup commit and approved the PR with it. Feel free to apply the merge label if this looks good to you or ask / push changes if you want us to iterate more. |
A Googler has manually verified that the CLAs look good. (Googler, please make sure the reason for overriding the CLA status is clearly documented in these comments.) |
52df2cd
to
71b72cd
Compare
So there's good news and bad news. 👍 The good news is that everyone that needs to sign a CLA (the pull request submitter and all commit authors) have done so. Everything is all good there. 😕 The bad news is that it appears that one or more commits were authored or co-authored by someone other than the pull request submitter. We need to confirm that all authors are ok with their commits being contributed to this project. Please have them confirm that here in the pull request. Note to project maintainer: This is a terminal state, meaning the |
A Googler has manually verified that the CLAs look good. (Googler, please make sure the reason for overriding the CLA status is clearly documented in these comments.) |
I'm good with the proposed changes |
Currently, DOM node removal called `removeChild` on the saved parent node when destroying a component. However, this will fail if the component has been manually moved in the DOM. This change makes the removal always use the node's real `parentNode` and ignore the provided `parent`.
71b72cd
to
cf528fa
Compare
So there's good news and bad news. 👍 The good news is that everyone that needs to sign a CLA (the pull request submitter and all commit authors) have done so. Everything is all good there. 😕 The bad news is that it appears that one or more commits were authored or co-authored by someone other than the pull request submitter. We need to confirm that all authors are ok with their commits being contributed to this project. Please have them confirm that here in the pull request. Note to project maintainer: This is a terminal state, meaning the |
A Googler has manually verified that the CLAs look good. (Googler, please make sure the reason for overriding the CLA status is clearly documented in these comments.) |
This issue has been automatically locked due to inactivity. Read more about our automatic conversation locking policy. This action has been performed automatically by a bot. |
Currently, DOM node removal called
removeChild
on the saved parentnode when destroying a component. However, this will fail if the
component has been manually moved in the DOM. This change makes the
removal always use the node's real
parentNode
and ignore the providedparent
.Reference: FW-977