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

bug: Failed to execute 'removeChild' on 'Node' #3278

Closed
3 tasks done
jeco123 opened this issue Mar 10, 2022 · 14 comments · Fixed by #5148
Closed
3 tasks done

bug: Failed to execute 'removeChild' on 'Node' #3278

jeco123 opened this issue Mar 10, 2022 · 14 comments · Fixed by #5148
Labels
Resolution: Refine This PR is marked for Jira refinement. We're not working on it - we're talking it through. slot-related

Comments

@jeco123
Copy link

jeco123 commented Mar 10, 2022

Prerequisites

Stencil Version

2.14.1

Current Behavior

I created a simple web component without parameters but with a slot inside using stencil. This component is bundled using the @stencil/react-output-target package (0.3.1).

@Component({
  tag: 'tds-grid',
})
export class Grid {
render() {
  return (<div>
    <slot />
  </div>
);

When the children of the component change dynamically, we got the Failed to execute 'removeChild' on 'Node' error.

This issue has been listed in the ionic-framework projet and is reproductible with stencil.
ionic-team/ionic-framework#18782

Expected Behavior

=> should not generate a fatal error and content must be rerender without crashing.

Steps to Reproduce

  1. Create a web component as describe in the current behaviour section
  2. Generate this component for react using the @stencil/react-output-target package
  3. Create a react application, import the generated react component and try to update the content of this component dynamically as it is described in the ionic framework issue bug: @ionic/react: ion-slides: Failed to execute 'removeChild' on 'Node' ionic-framework#18782

Code Reproduction URL

this code is easily reproductible => ionic-team/ionic-framework#18782

Additional Information

No response

@ionitron-bot ionitron-bot bot added the triage label Mar 10, 2022
@rwaskiewicz
Copy link
Member

Hey @jeco123 👋

Thanks for the bug report. Could you do me a favor and please create a minimal reproduction case for the team to pull down? While I understand that this appears to be the same as ionic-team/ionic-framework#18782, it'd be great to have something that's both 1) able to be quickly pulled down by the team without having to recreate the scenario by hand 2) using recent versions of the libraries involved. Thanks!

@rwaskiewicz rwaskiewicz added Bug: Needs Validation Awaiting Reply This PR or Issue needs a reply from the original reporter. and removed triage labels Mar 11, 2022
@jeco123
Copy link
Author

jeco123 commented Mar 15, 2022

Hi @rwaskiewicz

I'm gonna create a mono repo with a simple case.

Regards,

Jérôme

@ionitron-bot ionitron-bot bot added Reply Received and removed Awaiting Reply This PR or Issue needs a reply from the original reporter. labels Mar 15, 2022
@rwaskiewicz rwaskiewicz added Awaiting Reply This PR or Issue needs a reply from the original reporter. and removed Reply Received labels Mar 15, 2022
@jeco123
Copy link
Author

jeco123 commented Mar 17, 2022

Hi guys, here is my repo => https://github.com/jeco123/stencilbug.git

@ionitron-bot ionitron-bot bot added Reply Received and removed Awaiting Reply This PR or Issue needs a reply from the original reporter. labels Mar 17, 2022
@jeco123
Copy link
Author

jeco123 commented Mar 25, 2022

Just to add more info #2259

@rwaskiewicz rwaskiewicz added Resolution: Needs Investigation This PR or Issue should be investigated from the Stencil team and removed Bug: Needs Validation labels Mar 25, 2022
@danielleroux
Copy link

I'm facing the same issue.

I have a dropdown and dropdown-item as stencil webcomponent. I used the react-output-target to generate wrapper for react.
The component MyDropdown and MyDropdownItem is scoped=true but shadow=false.

example usage:

<div>
    <input
        type={'text'}
        onInput={(e) => setSearch((e.target as HTMLInputElement).value)}
    />
</div>
<MyDropdown>
    {items.filter(item => item.includes(search)).map(item => <MyDropdownItem key={item}  label={item} />)}
</MyDropdown>

if i start typing into the input field i get Uncaught DOMException: Failed to execute 'removeChild' on 'Node': The node to be removed is not a child of this node.

@jeco123
Copy link
Author

jeco123 commented Aug 2, 2022

Can you try to wrap your dropdown item into a div for exemple just to see if you have still the error ?I had another pb with vuejs, and wrapping that made my slot working!

@danielleroux
Copy link

danielleroux commented Aug 2, 2022

Sadly not. Its resulting into the same problem

<div>
    <input
        type={'text'}
        onInput={(e) => setSearch((e.target as HTMLInputElement).value)}
    />
</div>
<MyDropdown>
    {items.filter(item => item.includes(search)).map(item => <div key={item}><MyDropdownItem  label={item} /></div>)}
</MyDropdown>

If i enable the shadow dom on the MyDropdown its working, but for now its no option for us. I'm not so deep inside the technical implementation why shadow dom has so much affect into rendering slots 🤔

@jeco123
Copy link
Author

jeco123 commented Sep 12, 2022

Hi guys, any news about this subject ? Regards, Jérôme

@ammanvedi
Copy link

Seeing the same issue when shadow dom is disabled. Adding a child div seems to work for now.

As far as i see

  1. web component mounts in react
<mycomponent>
    <reactchild />
</mycomponent>

at this point this is the view react has of this in its virtual dom

  1. the web component mounts and may create extra divs between
<mycomponent>
    <div class="content-wrapper">
        <reactchild />
     </div>
</mycomponent>

this is the actual DOM, the view react has, has not changed since 1.

  1. some change happens that causes to unmount
  2. react expects to find reactchild at selector mycomponent > reactchild
  3. element cannot be found becuase webcomponent has created intermediate markup

@rwaskiewicz rwaskiewicz added slot-related Resolution: Refine This PR is marked for Jira refinement. We're not working on it - we're talking it through. and removed Resolution: Needs Investigation This PR or Issue should be investigated from the Stencil team labels Sep 6, 2023
tanner-reits added a commit that referenced this issue Dec 8, 2023
This commit adds a patch for an HtmlElement's `removeChild` method

Fixes: #3278 #2259

STENCIL-937

Co-authored-by: johnjenkins <johnljenkins@hotmail.com>
github-merge-queue bot pushed a commit that referenced this issue Dec 12, 2023
* fix(runtime): add patch for `removeChild` on `scoped` components

This commit adds a patch for an HtmlElement's `removeChild` method

Fixes: #3278 #2259

STENCIL-937

Co-authored-by: johnjenkins <johnljenkins@hotmail.com>

* add e2e tests

* PR feedback

Co-authored-by: Ryan Waskiewicz <ryanwaskiewicz@gmail.com>

---------

Co-authored-by: johnjenkins <johnljenkins@hotmail.com>
Co-authored-by: Ryan Waskiewicz <ryanwaskiewicz@gmail.com>
@rwaskiewicz
Copy link
Member

rwaskiewicz commented Dec 18, 2023

The fix for this issue has been released as a part of today's Stencil 4.9.0 release under the experimentalSlotFixes flag (docs).

@jeco123
Copy link
Author

jeco123 commented Feb 8, 2024

@rwaskiewicz,

Hi guys, i updated my repo with the stencil 4.12.1 release. The bug is already there… Did i miss something in the stencil config?

@rwaskiewicz
Copy link
Member

@jeco123 can you do me a favor and verify that experimentalSlotFixes is enabled in your Stencil config and that the issue is occurring in components that use scoped: true?

@jeco123
Copy link
Author

jeco123 commented Feb 8, 2024

@rwaskiewicz,

Here is the stencil config https://github.com/jeco123/stencilbug/blob/main/packages/web-components/stencil.config.ts.

export const config: Config = {
  namespace: 'web-components',
  extras: {
    experimentalSlotFixes: true,
  },

And here is the component https://github.com/jeco123/stencilbug/blob/main/packages/web-components/src/components/grid/Grid.tsx

import { Component, h } from '@stencil/core';

@Component({
  tag: 'my-grid',
})
export class Grid {
  render() {
    return (
      <div class="grid">
        <slot />
      </div>
    );
  }
}

@rwaskiewicz
Copy link
Member

Ah, okay - the lack of an encapsulation mode is the reason you're still seeing this. You need to set scoped: true or shadow: true in the @Component decorator for this fix to be applied

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Resolution: Refine This PR is marked for Jira refinement. We're not working on it - we're talking it through. slot-related
Projects
None yet
4 participants