Skip to content

Commit 272ad61

Browse files
committed
fix(injectors): reset the construction counter in dynamic strategy.
Adds tests for hydrate / dehydrate in cycle. Closes angular#3635
1 parent 5f7d4fa commit 272ad61

File tree

2 files changed

+48
-3
lines changed

2 files changed

+48
-3
lines changed

modules/angular2/src/core/compiler/element_injector.ts

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -673,7 +673,7 @@ export class ElementInjector extends TreeNode<ElementInjector> implements Depend
673673

674674
private _addViewQuery(queryRef: QueryRef, host: ElementInjector): void {
675675
if (isBlank(queryRef) || !queryRef.isViewQuery || this._hasQuery(queryRef)) return;
676-
if (host._query0.originator == host) {
676+
if (queryRef.originator == host) {
677677
// TODO(rado): Replace this.parent check with distanceToParent = 1 when
678678
// https://github.com/angular/angular/issues/2707 is fixed.
679679
if (!queryRef.query.descendants && isPresent(this.parent)) return;
@@ -863,8 +863,8 @@ export class ElementInjector extends TreeNode<ElementInjector> implements Depend
863863

864864
getRootViewInjectors(): ElementInjector[] {
865865
var view = this._preBuiltObjects.view;
866-
return view.getNestedView(view.elementOffset + this.getBoundElementIndex())
867-
.rootElementInjectors;
866+
var nestedView = view.getNestedView(view.elementOffset + this.getBoundElementIndex());
867+
return isPresent(nestedView) ? nestedView.rootElementInjectors : [];
868868
}
869869
}
870870

@@ -1068,6 +1068,7 @@ class ElementInjectorDynamicStrategy implements _ElementInjectorStrategy {
10681068
hydrate(): void {
10691069
var inj = this.injectorStrategy;
10701070
var p = inj.protoStrategy;
1071+
inj.resetConstructionCounter();
10711072

10721073
for (var i = 0; i < p.keyIds.length; i++) {
10731074
if (p.bindings[i] instanceof DirectiveBinding && isPresent(p.keyIds[i]) &&

modules/angular2/test/core/compiler/element_injector_spec.ts

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@ import {
3535
import {
3636
Attribute,
3737
Query,
38+
ViewQuery,
3839
ComponentMetadata,
3940
DirectiveMetadata,
4041
LifecycleEvent
@@ -51,9 +52,11 @@ import {QueryList} from 'angular2/src/core/compiler/query_list';
5152
@IMPLEMENTS(AppView)
5253
class DummyView extends SpyObject {
5354
changeDetector;
55+
elementOffset: number;
5456
constructor() {
5557
super(AppView);
5658
this.changeDetector = null;
59+
this.elementOffset = 0;
5760
}
5861
noSuchMethod(m) { return super.noSuchMethod(m); }
5962
}
@@ -159,6 +162,12 @@ class NeedsQuery {
159162
constructor(@Query(CountingDirective) query: QueryList<CountingDirective>) { this.query = query; }
160163
}
161164

165+
@Injectable()
166+
class NeedsViewQuery {
167+
query: QueryList<CountingDirective>;
168+
constructor(@ViewQuery(CountingDirective) query: QueryList<CountingDirective>) { this.query = query; }
169+
}
170+
162171
@Injectable()
163172
class NeedsQueryByVarBindings {
164173
query: QueryList<any>;
@@ -850,6 +859,41 @@ export function main() {
850859
});
851860
});
852861

862+
describe("getRootViewInjectors", () => {
863+
it("should return an empty array if there is no nested view", () => {
864+
var inj = injector(extraBindings);
865+
expect(inj.getRootViewInjectors()).toEqual([]);
866+
});
867+
});
868+
869+
describe("dehydrate", () => {
870+
function cycleHydrate(inj: ElementInjector, host=null): void {
871+
// Each injection supports 3 query slots, so we cycle 4 times.
872+
for (var i = 0; i < 4; i++) {
873+
inj.dehydrate();
874+
inj.hydrate(null, host, defaultPreBuiltObjects);
875+
}
876+
}
877+
878+
it("should handle repeated hydration / dehydration", () => {
879+
var inj = injector(extraBindings);
880+
cycleHydrate(inj);
881+
});
882+
883+
it("should handle repeated hydration / dehydration with query present", () => {
884+
var inj = injector(ListWrapper.concat([NeedsQuery], extraBindings));
885+
cycleHydrate(inj);
886+
});
887+
888+
889+
it("should handle repeated hydration / dehydration with view query present", () => {
890+
var inj = injector(extraBindings);
891+
var host = injector(ListWrapper.concat([NeedsViewQuery], extraBindings));
892+
893+
cycleHydrate(inj, host);
894+
});
895+
});
896+
853897
describe("lifecycle", () => {
854898
it("should call onDestroy on directives subscribed to this event", () => {
855899
var inj = injector(ListWrapper.concat(

0 commit comments

Comments
 (0)