Skip to content

Commit

Permalink
revert: fix(ivy): remove query results from destroyed embedded views (#…
Browse files Browse the repository at this point in the history
…28445)

This reverts commit 71b9d55.
  • Loading branch information
matsko committed Feb 4, 2019
1 parent 4dfcbc6 commit 52d3795
Show file tree
Hide file tree
Showing 3 changed files with 19 additions and 31 deletions.
24 changes: 6 additions & 18 deletions packages/core/src/render3/node_manipulation.ts
Expand Up @@ -11,7 +11,7 @@ import {attachPatchData} from './context_discovery';
import {callHooks} from './hooks';
import {LContainer, NATIVE, VIEWS, unusedValueExportToPlacateAjd as unused1} from './interfaces/container';
import {ComponentDef} from './interfaces/definition';
import {TContainerNode, TElementContainerNode, TElementNode, TNode, TNodeFlags, TNodeType, TViewNode, unusedValueExportToPlacateAjd as unused2} from './interfaces/node';
import {TContainerNode, TElementContainerNode, TElementNode, TNode, TNodeFlags, TNodeType, TProjectionNode, TViewNode, unusedValueExportToPlacateAjd as unused2} from './interfaces/node';
import {unusedValueExportToPlacateAjd as unused3} from './interfaces/projection';
import {ProceduralRenderer3, RComment, RElement, RNode, RText, Renderer3, isProceduralRenderer, unusedValueExportToPlacateAjd as unused4} from './interfaces/renderer';
import {CLEANUP, CONTAINER_INDEX, FLAGS, HEADER_OFFSET, HOST_NODE, HookData, LView, LViewFlags, NEXT, PARENT, QUERIES, RENDERER, TVIEW, unusedValueExportToPlacateAjd as unused5} from './interfaces/view';
Expand Down Expand Up @@ -242,17 +242,14 @@ export function destroyViewTree(rootView: LView): void {
while (viewOrContainer) {
let next: LView|LContainer|null = null;

if (isLContainer(viewOrContainer)) {
// If container, traverse down to its first LView.
const container = viewOrContainer as LContainer;
const viewsInContainer = container[VIEWS];
if (viewsInContainer.length) {
next = viewsInContainer[0];
}
} else {
if (viewOrContainer.length >= HEADER_OFFSET) {
// If LView, traverse down to child.
const view = viewOrContainer as LView;
if (view[TVIEW].childIndex > -1) next = getLViewChild(view);
} else {
// If container, traverse down to its first LView.
const container = viewOrContainer as LContainer;
if (container[VIEWS].length) next = container[VIEWS][0];
}

if (next == null) {
Expand All @@ -261,15 +258,6 @@ export function destroyViewTree(rootView: LView): void {
while (viewOrContainer && !viewOrContainer ![NEXT] && viewOrContainer !== rootView) {
cleanUpView(viewOrContainer);
viewOrContainer = getParentState(viewOrContainer, rootView);
if (isLContainer(viewOrContainer)) {
// this view will be destroyed so we need to notify queries that a view is detached
const viewsInContainer = (viewOrContainer as LContainer)[VIEWS];
for (let viewToDetach of viewsInContainer) {
if (viewToDetach[QUERIES]) {
viewToDetach[QUERIES] !.removeView();
}
}
}
}
cleanUpView(viewOrContainer || rootView);
next = viewOrContainer && viewOrContainer ![NEXT];
Expand Down
3 changes: 1 addition & 2 deletions packages/core/src/render3/util.ts
Expand Up @@ -127,8 +127,7 @@ export function isComponentDef<T>(def: DirectiveDef<T>): def is ComponentDef<T>
return (def as ComponentDef<T>).template !== null;
}

export function isLContainer(
value: RElement | RComment | LContainer | LView | StylingContext | null): boolean {
export function isLContainer(value: RElement | RComment | LContainer | StylingContext): boolean {
// Styling contexts are also arrays, but their first index contains an element node
return Array.isArray(value) && value.length === LCONTAINER_LENGTH;
}
Expand Down
23 changes: 12 additions & 11 deletions packages/core/test/linker/query_integration_spec.ts
Expand Up @@ -633,24 +633,25 @@ describe('Query API', () => {
expect(q.query.map((d: TextDirective) => d.text)).toEqual(['2', '1']);
});

it('should remove manually projected templates if their parent view is destroyed', () => {
const template = `
fixmeIvy('FW-920: Queries in nested views are not destroyed properly')
.it('should remove manually projected templates if their parent view is destroyed', () => {
const template = `
<manual-projecting #q><ng-template #tpl><div text="1"></div></ng-template></manual-projecting>
<div *ngIf="shouldShow">
<ng-container [ngTemplateOutlet]="tpl"></ng-container>
</div>
`;
const view = createTestCmp(MyComp0, template);
const q = view.debugElement.children[0].references !['q'];
view.componentInstance.shouldShow = true;
view.detectChanges();
const view = createTestCmp(MyComp0, template);
const q = view.debugElement.children[0].references !['q'];
view.componentInstance.shouldShow = true;
view.detectChanges();

expect(q.query.length).toBe(1);
expect(q.query.length).toBe(1);

view.componentInstance.shouldShow = false;
view.detectChanges();
expect(q.query.length).toBe(0);
});
view.componentInstance.shouldShow = false;
view.detectChanges();
expect(q.query.length).toBe(0);
});

modifiedInIvy('https://github.com/angular/angular/issues/15117 fixed in ivy')
.it('should not throw if a content template is queried and created in the view during change detection',
Expand Down

0 comments on commit 52d3795

Please sign in to comment.