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

componentWillUnmount not firing for a root component that renders null. #538

Closed
joeldenning opened this issue Feb 8, 2017 · 4 comments
Closed
Labels
Projects
Milestone

Comments

@joeldenning
Copy link

Somewhat related to #392, #373, and #536. See https://jsfiddle.net/7d3tojb1/ for repro -- it uses preact@7.2.0.

The problem is that if you have a root component that renders null, then preact does not call componentWillUnmount on that component.

class Nothing extends preact.Component {
  render() {
  	console.log('rendering Nothing')
  	return null;
  }
  componentWillUnmount() {
  	calledCWU = true;
  	console.log('componentWillUnmount Nothing')
  }
}
const nothingRoot = preact.render(preact.h(Nothing, {}), document.body);

// This should unmount the component
preact.render('', document.body, nothingRoot);
@joeldenning
Copy link
Author

Seems related to https://github.com/developit/preact/blob/master/src/vdom/diff.js#L81-L95 -- rendering null seems to create a text node which goes into that if statement when things are being unmounted. The return dom short circuits the idiff function such that componentWillUnmount is never called.

@developit
Copy link
Member

Ah interesting - I had thought this was related more to PFC's, you're right it's because of the early bailout for text nodes. Seems like we just need to move the component handling on L98 to happen before the Text node shortcircuiting?

@joeldenning
Copy link
Author

I tried moving the component handling on L98 above the Text node shortcircuiting, but it didn't seem to help. In my example case, vnode === null, which then turns into vnode = '' on https://github.com/developit/preact/blob/master/src/vdom/diff.js#L77. So the if (isFunction(vnode.nodeName)) check on L98 isn't truthy and the buildComponentFromVNode function is not getting called.

This is my first venture into the preact source so I am still figuring out what a solution would look like, but I'll keep investigating.

@developit
Copy link
Member

Ah yes, sorry my brain was still associating this with components. Maybe rendering a Comment node for component roots would fix this because it'd skip the shortcircuiting? You'd hit the comment node shortcircuit for component A -> B, but that'd be triggered from renderComponent(), which handles unmounting mismatched components by itself.

@developit developit added this to the 8.0 milestone Feb 21, 2017
@developit developit added this to In Progress in 8.0 Mar 9, 2017
@developit developit moved this from In Progress to Code-Complete in 8.0 Mar 13, 2017
@developit developit moved this from Code-Complete to Merged in 8.0 Apr 6, 2017
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
No open projects
8.0
Merged
Development

No branches or pull requests

2 participants