perf(change_detection): do not check intermediate results
This commit is contained in:
@@ -304,6 +304,7 @@ var _availableDefinitions = [
|
||||
'{z: 1}',
|
||||
'{z: a}',
|
||||
'name | pipe',
|
||||
'(name | pipe).length',
|
||||
"name | pipe:'one':address.city",
|
||||
'value',
|
||||
'a',
|
||||
|
||||
@@ -351,6 +351,14 @@ export function main() {
|
||||
val.changeDetector.detectChanges();
|
||||
expect(val.dispatcher.loggedValues).toEqual(['value one two default']);
|
||||
});
|
||||
|
||||
it('should support pipes as arguments to pure functions', () => {
|
||||
var registry = new FakePipes('pipe', () => new IdentityPipe());
|
||||
var person = new Person('bob');
|
||||
var val = _createChangeDetector('(name | pipe).length', person, registry);
|
||||
val.changeDetector.detectChanges();
|
||||
expect(val.dispatcher.loggedValues).toEqual([3]);
|
||||
});
|
||||
});
|
||||
|
||||
it('should notify the dispatcher on all changes done', () => {
|
||||
|
||||
@@ -7,14 +7,22 @@ import {DirectiveIndex} from 'angular2/src/change_detection/directive_record';
|
||||
|
||||
export function main() {
|
||||
function r(funcOrValue, args, contextIndex, selfIndex,
|
||||
{lastInBinding, mode, name, directiveIndex}:
|
||||
{lastInBinding?: any, mode?: any, name?: any, directiveIndex?: any} = {}) {
|
||||
{lastInBinding, mode, name, directiveIndex, argumentToPureFunction}: {
|
||||
lastInBinding?: any,
|
||||
mode?: any,
|
||||
name?: any,
|
||||
directiveIndex?: any,
|
||||
argumentToPureFunction?: boolean
|
||||
} = {}) {
|
||||
if (isBlank(lastInBinding)) lastInBinding = false;
|
||||
if (isBlank(mode)) mode = RecordType.PROPERTY;
|
||||
if (isBlank(name)) name = "name";
|
||||
if (isBlank(directiveIndex)) directiveIndex = null;
|
||||
if (isBlank(argumentToPureFunction)) argumentToPureFunction = false;
|
||||
|
||||
return new ProtoRecord(mode, name, funcOrValue, args, null, contextIndex, directiveIndex,
|
||||
selfIndex, null, null, lastInBinding, false);
|
||||
selfIndex, null, null, lastInBinding, false, argumentToPureFunction,
|
||||
false);
|
||||
}
|
||||
|
||||
describe("change detection - coalesce", () => {
|
||||
@@ -56,7 +64,14 @@ export function main() {
|
||||
[r("user", [], 0, 1, {lastInBinding: true}), r("user", [], 0, 2, {lastInBinding: true})]);
|
||||
|
||||
expect(rs[1]).toEqual(new ProtoRecord(RecordType.SELF, "self", null, [], null, 1, null, 2,
|
||||
null, null, true, false));
|
||||
null, null, true, false, false, false));
|
||||
});
|
||||
|
||||
it("should set referencedBySelf", () => {
|
||||
var rs = coalesce(
|
||||
[r("user", [], 0, 1, {lastInBinding: true}), r("user", [], 0, 2, {lastInBinding: true})]);
|
||||
|
||||
expect(rs[0].referencedBySelf).toBeTruthy();
|
||||
});
|
||||
|
||||
it("should not coalesce directive lifecycle records", () => {
|
||||
@@ -88,5 +103,26 @@ export function main() {
|
||||
]);
|
||||
expect(rs.length).toEqual(4);
|
||||
});
|
||||
|
||||
it('should preserve the argumentToPureFunction property', () => {
|
||||
var rs = coalesce([
|
||||
r("user", [], 0, 1),
|
||||
r("user", [], 0, 2, {argumentToPureFunction: true}),
|
||||
r("user", [], 0, 3),
|
||||
r("name", [], 3, 4)
|
||||
]);
|
||||
expect(rs)
|
||||
.toEqual([r("user", [], 0, 1, {argumentToPureFunction: true}), r("name", [], 1, 2)]);
|
||||
});
|
||||
|
||||
it('should preserve the argumentToPureFunction property (the original record)', () => {
|
||||
var rs = coalesce([
|
||||
r("user", [], 0, 1, {argumentToPureFunction: true}),
|
||||
r("user", [], 0, 2),
|
||||
r("name", [], 2, 3)
|
||||
]);
|
||||
expect(rs)
|
||||
.toEqual([r("user", [], 0, 1, {argumentToPureFunction: true}), r("name", [], 1, 2)]);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
@@ -0,0 +1,38 @@
|
||||
import {
|
||||
ddescribe,
|
||||
describe,
|
||||
it,
|
||||
iit,
|
||||
xit,
|
||||
expect,
|
||||
beforeEach,
|
||||
afterEach,
|
||||
inject
|
||||
} from 'angular2/test_lib';
|
||||
|
||||
import {ProtoRecordBuilder} from 'angular2/src/change_detection/proto_change_detector';
|
||||
import {BindingRecord} from 'angular2/src/change_detection/binding_record';
|
||||
import {Parser} from 'angular2/src/change_detection/parser/parser';
|
||||
|
||||
export function main() {
|
||||
describe("ProtoRecordBuilder", () => {
|
||||
it('should set argumentToPureFunction flag', inject([Parser], (p: Parser) => {
|
||||
var builder = new ProtoRecordBuilder();
|
||||
var ast = p.parseBinding("[1,2]", "location"); // collection literal is a pure function
|
||||
builder.add(BindingRecord.createForElementProperty(ast, 0, "property"), []);
|
||||
|
||||
var isPureFunc = builder.records.map(r => r.argumentToPureFunction);
|
||||
expect(isPureFunc).toEqual([true, true, false]);
|
||||
}));
|
||||
|
||||
it('should not set argumentToPureFunction flag when not needed',
|
||||
inject([Parser], (p: Parser) => {
|
||||
var builder = new ProtoRecordBuilder();
|
||||
var ast = p.parseBinding("f(1,2)", "location");
|
||||
builder.add(BindingRecord.createForElementProperty(ast, 0, "property"), []);
|
||||
|
||||
var isPureFunc = builder.records.map(r => r.argumentToPureFunction);
|
||||
expect(isPureFunc).toEqual([false, false, false]);
|
||||
}));
|
||||
});
|
||||
}
|
||||
@@ -0,0 +1,58 @@
|
||||
import {ddescribe, describe, it, iit, xit, expect, beforeEach, afterEach} from 'angular2/test_lib';
|
||||
import {isBlank} from 'angular2/src/facade/lang';
|
||||
|
||||
import {RecordType, ProtoRecord} from 'angular2/src/change_detection/proto_record';
|
||||
|
||||
export function main() {
|
||||
function r({lastInBinding, mode, name, directiveIndex, argumentToPureFunction, referencedBySelf}:
|
||||
{
|
||||
lastInBinding?: any,
|
||||
mode?: any,
|
||||
name?: any,
|
||||
directiveIndex?: any,
|
||||
argumentToPureFunction?: boolean,
|
||||
referencedBySelf?: boolean
|
||||
} = {}) {
|
||||
if (isBlank(lastInBinding)) lastInBinding = false;
|
||||
if (isBlank(mode)) mode = RecordType.PROPERTY;
|
||||
if (isBlank(name)) name = "name";
|
||||
if (isBlank(directiveIndex)) directiveIndex = null;
|
||||
if (isBlank(argumentToPureFunction)) argumentToPureFunction = false;
|
||||
if (isBlank(referencedBySelf)) referencedBySelf = false;
|
||||
|
||||
return new ProtoRecord(mode, name, null, [], null, 0, directiveIndex, 0, null, null,
|
||||
lastInBinding, false, argumentToPureFunction, referencedBySelf);
|
||||
}
|
||||
|
||||
describe("ProtoRecord", () => {
|
||||
describe('shouldBeChecked', () => {
|
||||
it('should be true for pure functions', () => {
|
||||
expect(r({mode: RecordType.COLLECTION_LITERAL}).shouldBeChecked()).toBeTruthy();
|
||||
});
|
||||
|
||||
it('should be true for args of pure functions', () => {
|
||||
expect(r({mode: RecordType.CONST, argumentToPureFunction: true}).shouldBeChecked())
|
||||
.toBeTruthy();
|
||||
});
|
||||
|
||||
it('should be true for last in binding records', () => {
|
||||
expect(r({mode: RecordType.CONST, lastInBinding: true}).shouldBeChecked()).toBeTruthy();
|
||||
});
|
||||
|
||||
it('should be false otherwise',
|
||||
() => { expect(r({mode: RecordType.CONST}).shouldBeChecked()).toBeFalsy(); });
|
||||
});
|
||||
|
||||
describe('isUsedByOtherRecord', () => {
|
||||
it('should be false for lastInBinding records',
|
||||
() => { expect(r({lastInBinding: true}).isUsedByOtherRecord()).toBeFalsy(); });
|
||||
|
||||
it('should be true for lastInBinding records that are referenced by self records', () => {
|
||||
expect(r({lastInBinding: true, referencedBySelf: true}).isUsedByOtherRecord()).toBeTruthy();
|
||||
});
|
||||
|
||||
it('should be true for non lastInBinding records',
|
||||
() => { expect(r({lastInBinding: false}).isUsedByOtherRecord()).toBeTruthy(); });
|
||||
});
|
||||
});
|
||||
}
|
||||
+2
-6
@@ -38,9 +38,8 @@ class _MyComponent_ChangeDetector0
|
||||
var l_context = this.context,
|
||||
l_myNum0,
|
||||
c_myNum0,
|
||||
l_interpolate1,
|
||||
c_interpolate1;
|
||||
c_myNum0 = c_interpolate1 = false;
|
||||
l_interpolate1;
|
||||
c_myNum0 = false;
|
||||
var isChanged = false;
|
||||
var changes = null;
|
||||
|
||||
@@ -56,7 +55,6 @@ class _MyComponent_ChangeDetector0
|
||||
l_interpolate1 =
|
||||
"Salad: " "${l_myNum0 == null ? "" : l_myNum0}" " is awesome";
|
||||
if (_gen.looseNotIdentical(l_interpolate1, this.interpolate1)) {
|
||||
c_interpolate1 = true;
|
||||
if (throwOnChange) {
|
||||
_gen.ChangeDetectionUtil.throwOnChange(this.currentProto,
|
||||
_gen.ChangeDetectionUtil.simpleChange(
|
||||
@@ -68,8 +66,6 @@ class _MyComponent_ChangeDetector0
|
||||
|
||||
this.interpolate1 = l_interpolate1;
|
||||
}
|
||||
} else {
|
||||
l_interpolate1 = this.interpolate1;
|
||||
}
|
||||
changes = null;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user