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鈥檒l occasionally send you account related emails.
Already on GitHub? Sign in to your account
ComponentRef<T> onDestroyed() callback does not get called #39365
Comments
Thanks for the report and for the reproduction! We've done an investigation and this is related to an item mentioned on the Ivy Compatibility guide, specifically the one related to no longer being able to overwrite hooks on directive instances. The investigation found a difference in how Ivy handles componentRef and componentInstance compared to ViewEngine. In Ivy, the callback provided in the A workaround is to manually call |
@jessicajaniuk Thanks for the info. Is it possible to get the Pseudo code ahead: ...
export class SomeComponent implements OnDestroy {
constructor(private compRef: ComponentRef<SomeComponent>) { }
public ngOnDestroy(): void {
this.compRef.destroy();
}
} This would be cool... if that's not possible I would have to set the `componentRef`` instance manually via a setter or method. |
@FSDRE Is your pseudocode example referring to the child component scope or the parent component that's using the |
@jessicajaniuk The pseudocode is the dynamically created component. The thing is, the reproduction is only that. In the real application I do not always destory the component via |
A lot of things to unpack here. First, the documentation for Not a single mention about being able to call this method multiple times and each of the callbacks are placed in an array and iterated over when destroyed. And strictly speaking, the behavior exhibited in this issue report appears to be consistent with the documentation, which states the callback function is called when the View Engine: Second, and probably even more alarming, is that the this.compRef.onDestroy(() =>
console.log("DynamicComponent onDestroyed callback")
); to // this.compRef.onDestroy(() =>
this.compRef.hostView.onDestroy(() =>
console.log("DynamicComponent onDestroyed callback")
); You would also expect this callback to be invoked in both destruction scenarios, but it is called in neither in Ivy! angular/packages/core/src/render3/instructions/shared.ts Lines 753 to 761 in d939b5f
I don't know why the if (tView.firstCreatePass){
} conditional is even there and it is blocking the callbacks from being stored. Manually setting (this.compRef.hostView as any)._lView[1].firstCreatePass = true; So @FSDRE , the final workaround looks like this: const TVIEW = 1;
const tView = (this.compRef.hostView as any)._lView[TVIEW];
tView.firstCreatePass = true;
// Put callback on the host view instead of the component ref.
this.compRef.hostView.onDestroy(() =>
console.log("DynamicComponent onDestroyed callback")
);
tView.firstCreatePass = false; //...I guess? And to add even more confusion and gotchas, the calling order here in Ivy is
@jessicajaniuk A similar problem (internal view not knowing about it's |
@Achilles1515 Thank you very much for your input! That's some "big oooof's" right there. I am not keen on implementing such hacky workarounds in production code that might break again in a couple updates. I think I will register my Is there an EOL date for VE? I have reported at least 3 similar messed up issues regarding Ivy and so far I don't see anything happening other than auto-locking. Currently Ivy creates more problems than it solves, unfortunately. Maybe the release was a bit rushed. |
Hi, just want to give a quick update: the issue with the |
Closing this ticket since the corresponding PR #39876 was merged and the changes will be available after the next patch release (v11.0.4). Thank you. |
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. |
馃悶 bug report
Affected Package
The issue is caused by package @angular/coreIs this a regression?
Yes, the previous version in which this bug was not present was: Pre-Ivy or if you disable IvyDescription
Problem: ComponentRef.onDestroyed callback does not get called
A component gets dynamically created via
ComponentFactoryResolver
. It is then inserted into the view.As you can see, the
onDestroyed
callback is attached. If the component gets destroyed by its ComponentRef, the callback gets called correctly like so:if the component gets destroyed by clearing the
anchor
, the callback does not get called:As far as I can tell, the
onDestroyed
callback ONLY gets called when the component gets destroyed by itsComponentRef
. Whenever the component gets destroyed by clearing parent views or navigating away or data binding, the callback does not get called.It works in NG 8.2.14 and it works if you set
enableIvy: false
in tsconfig.json.馃敩 Minimal Reproduction
https://stackblitz.com/edit/angular-ivy-ev4v2y
馃實 Your Environment
Angular Version:
The text was updated successfully, but these errors were encountered: