diff --git a/packages/core/src/render3/component_ref.ts b/packages/core/src/render3/component_ref.ts index 7fe055caf5..0462394ac9 100644 --- a/packages/core/src/render3/component_ref.ts +++ b/packages/core/src/render3/component_ref.ts @@ -265,6 +265,7 @@ export class ComponentRef extends viewEngine_ComponentRef { ngDevMode && assertDefined(this.destroyCbs, 'NgModule already destroyed'); this.destroyCbs !.forEach(fn => fn()); this.destroyCbs = null; + this.hostView.destroy(); } onDestroy(callback: () => void): void { ngDevMode && assertDefined(this.destroyCbs, 'NgModule already destroyed'); diff --git a/packages/core/src/render3/view_engine_compatibility.ts b/packages/core/src/render3/view_engine_compatibility.ts index e1bec3c745..9246335101 100644 --- a/packages/core/src/render3/view_engine_compatibility.ts +++ b/packages/core/src/render3/view_engine_compatibility.ts @@ -265,6 +265,9 @@ export function createContainerRef( } move(viewRef: viewEngine_ViewRef, newIndex: number): viewEngine_ViewRef { + if (viewRef.destroyed) { + throw new Error('Cannot move a destroyed View in a ViewContainer!'); + } const index = this.indexOf(viewRef); this.detach(index); this.insert(viewRef, this._adjustIndex(newIndex)); diff --git a/packages/core/test/linker/integration_spec.ts b/packages/core/test/linker/integration_spec.ts index c33b6cd704..6f9dfb96f4 100644 --- a/packages/core/test/linker/integration_spec.ts +++ b/packages/core/test/linker/integration_spec.ts @@ -995,17 +995,18 @@ function declareTests(config?: {useJit: boolean}) { expect(dir.receivedArgs).toEqual(['one', undefined]); }); - fixmeIvy('unknown') && it('should not allow pipes in hostListeners', () => { - @Directive({selector: '[host-listener]', host: {'(click)': 'doIt() | somePipe'}}) - class DirectiveWithHostListener { - } + fixmeIvy('FW-742: Pipes in host listeners should throw a descriptive error') && + it('should not allow pipes in hostListeners', () => { + @Directive({selector: '[host-listener]', host: {'(click)': 'doIt() | somePipe'}}) + class DirectiveWithHostListener { + } - TestBed.configureTestingModule({declarations: [MyComp, DirectiveWithHostListener]}); - const template = '
'; - TestBed.overrideComponent(MyComp, {set: {template}}); - expect(() => TestBed.createComponent(MyComp)) - .toThrowError(/Cannot have a pipe in an action expression/); - }); + TestBed.configureTestingModule({declarations: [MyComp, DirectiveWithHostListener]}); + const template = '
'; + TestBed.overrideComponent(MyComp, {set: {template}}); + expect(() => TestBed.createComponent(MyComp)) + .toThrowError(/Cannot have a pipe in an action expression/); + }); @@ -1238,37 +1239,35 @@ function declareTests(config?: {useJit: boolean}) { }); describe('.insert', () => { - fixmeIvy('unknown') && - it('should throw with destroyed views', async(() => { - const fixture = TestBed.configureTestingModule({schemas: [NO_ERRORS_SCHEMA]}) - .createComponent(MyComp); - const tc = fixture.debugElement.children[0].children[0]; - const dynamicVp: DynamicViewport = tc.injector.get(DynamicViewport); - const ref = dynamicVp.create(); - fixture.detectChanges(); + it('should throw with destroyed views', async(() => { + const fixture = TestBed.configureTestingModule({schemas: [NO_ERRORS_SCHEMA]}) + .createComponent(MyComp); + const tc = fixture.debugElement.children[0].children[0]; + const dynamicVp: DynamicViewport = tc.injector.get(DynamicViewport); + const ref = dynamicVp.create(); + fixture.detectChanges(); - ref.destroy(); - expect(() => { - dynamicVp.insert(ref.hostView); - }).toThrowError('Cannot insert a destroyed View in a ViewContainer!'); - })); + ref.destroy(); + expect(() => { + dynamicVp.insert(ref.hostView); + }).toThrowError('Cannot insert a destroyed View in a ViewContainer!'); + })); }); describe('.move', () => { - fixmeIvy('unknown') && - it('should throw with destroyed views', async(() => { - const fixture = TestBed.configureTestingModule({schemas: [NO_ERRORS_SCHEMA]}) - .createComponent(MyComp); - const tc = fixture.debugElement.children[0].children[0]; - const dynamicVp: DynamicViewport = tc.injector.get(DynamicViewport); - const ref = dynamicVp.create(); - fixture.detectChanges(); + it('should throw with destroyed views', async(() => { + const fixture = TestBed.configureTestingModule({schemas: [NO_ERRORS_SCHEMA]}) + .createComponent(MyComp); + const tc = fixture.debugElement.children[0].children[0]; + const dynamicVp: DynamicViewport = tc.injector.get(DynamicViewport); + const ref = dynamicVp.create(); + fixture.detectChanges(); - ref.destroy(); - expect(() => { - dynamicVp.move(ref.hostView, 1); - }).toThrowError('Cannot move a destroyed View in a ViewContainer!'); - })); + ref.destroy(); + expect(() => { + dynamicVp.move(ref.hostView, 1); + }).toThrowError('Cannot move a destroyed View in a ViewContainer!'); + })); }); });