fix(core): various minor compiler fixes

Closes #8162
This commit is contained in:
Tobias Bosch
2016-04-20 18:10:19 -07:00
parent 9889c21aaa
commit 2f7045720a
8 changed files with 216 additions and 37 deletions

View File

@ -0,0 +1,150 @@
import {
AsyncTestCompleter,
beforeEach,
ddescribe,
xdescribe,
describe,
el,
dispatchEvent,
expect,
iit,
inject,
beforeEachProviders,
it,
xit,
containsRegexp,
stringifyElement,
TestComponentBuilder,
fakeAsync,
tick,
clearPendingTimers,
ComponentFixture
} from 'angular2/testing_internal';
import {IS_DART} from 'angular2/src/facade/lang';
import {
Component,
Pipe,
PipeTransform,
provide,
ViewMetadata,
PLATFORM_PIPES,
OpaqueToken,
Injector
} from 'angular2/core';
import {CompilerConfig} from 'angular2/compiler';
export function main() {
if (IS_DART) {
declareTests(false);
} else {
describe('jit', () => {
beforeEachProviders(
() => [provide(CompilerConfig, {useValue: new CompilerConfig(true, false, true)})]);
declareTests(true);
});
describe('no jit', () => {
beforeEachProviders(
() => [provide(CompilerConfig, {useValue: new CompilerConfig(true, false, false)})]);
declareTests(false);
});
}
}
function declareTests(isJit: boolean) {
// Place to put reproductions for regressions
describe('regressions', () => {
describe('platform pipes', () => {
beforeEachProviders(() => [provide(PLATFORM_PIPES, {useValue: [PlatformPipe], multi: true})]);
it('should overwrite them by custom pipes',
inject([TestComponentBuilder, AsyncTestCompleter], (tcb: TestComponentBuilder, async) => {
tcb.overrideView(
MyComp, new ViewMetadata({template: '{{true | somePipe}}', pipes: [CustomPipe]}))
.createAsync(MyComp)
.then((fixture) => {
fixture.detectChanges();
expect(fixture.nativeElement).toHaveText('someCustomPipe');
async.done();
});
}));
});
describe('providers', () => {
function createInjector(tcb: TestComponentBuilder, proviers: any[]): Promise<Injector> {
return tcb.overrideProviders(MyComp, [proviers])
.createAsync(MyComp)
.then((fixture) => fixture.componentInstance.injector);
}
it('should support providers with an OpaqueToken that contains a `.` in the name',
inject([TestComponentBuilder, AsyncTestCompleter], (tcb: TestComponentBuilder, async) => {
var token = new OpaqueToken('a.b');
var tokenValue = 1;
createInjector(tcb, [provide(token, {useValue: tokenValue})])
.then((injector: Injector) => {
expect(injector.get(token)).toEqual(tokenValue);
async.done();
});
}));
it('should support providers with an anonymous function',
inject([TestComponentBuilder, AsyncTestCompleter], (tcb: TestComponentBuilder, async) => {
var token = () => true;
var tokenValue = 1;
createInjector(tcb, [provide(token, {useValue: tokenValue})])
.then((injector: Injector) => {
expect(injector.get(token)).toEqual(tokenValue);
async.done();
});
}));
it('should support providers with an OpaqueToken that has a StringMap as value',
inject([TestComponentBuilder, AsyncTestCompleter], (tcb: TestComponentBuilder, async) => {
var token1 = new OpaqueToken('someToken');
var token2 = new OpaqueToken('someToken');
var tokenValue1 = {'a': 1};
var tokenValue2 = {'a': 1};
createInjector(
tcb,
[provide(token1, {useValue: tokenValue1}), provide(token2, {useValue: tokenValue2})])
.then((injector: Injector) => {
expect(injector.get(token1)).toEqual(tokenValue1);
expect(injector.get(token2)).toEqual(tokenValue2);
async.done();
});
}));
});
it('should allow logging a previous elements class binding via interpolation',
inject([TestComponentBuilder, AsyncTestCompleter], (tcb: TestComponentBuilder, async) => {
tcb.overrideTemplate(MyComp, `<div [class.a]="true" #el>Class: {{el.className}}</div>`)
.createAsync(MyComp)
.then((fixture) => {
fixture.detectChanges();
expect(fixture.nativeElement).toHaveText('Class: a');
async.done();
});
}));
});
}
@Component({selector: 'my-comp', template: ''})
class MyComp {
constructor(public injector: Injector) {}
}
@Pipe({name: 'somePipe', pure: true})
class PlatformPipe implements PipeTransform {
transform(value: any, args: any[]): any { return 'somePlatformPipe'; }
}
@Pipe({name: 'somePipe', pure: true})
class CustomPipe implements PipeTransform {
transform(value: any, args: any[]): any { return 'someCustomPipe'; }
}

View File

@ -88,6 +88,8 @@ const ALL_PIPES = CONST_EXPR([
forwardRef(() => PipeNeedsService),
forwardRef(() => PurePipe),
forwardRef(() => ImpurePipe),
forwardRef(() => DuplicatePipe1),
forwardRef(() => DuplicatePipe2),
]);
@Directive({selector: '[simpleDirective]'})
@ -254,6 +256,15 @@ export class PipeNeedsService implements PipeTransform {
transform(value: any, args: any[] = null): any { return this; }
}
@Pipe({name: 'duplicatePipe'})
export class DuplicatePipe1 implements PipeTransform {
transform(value: any, args: any[] = null): any { return this; }
}
@Pipe({name: 'duplicatePipe'})
export class DuplicatePipe2 implements PipeTransform {
transform(value: any, args: any[] = null): any { return this; }
}
@Component({selector: 'root'})
class TestComp {
@ -628,6 +639,11 @@ export function main() {
expect(el.children[0].inject(SimpleDirective).value.service).toEqual('pipeService');
}));
it('should overwrite pipes with later entry in the pipes array', fakeAsync(() => {
var el = createComp('<div [simpleDirective]="true | duplicatePipe"></div>', tcb);
expect(el.children[0].inject(SimpleDirective).value).toBeAnInstanceOf(DuplicatePipe2);
}));
it('should inject ChangeDetectorRef into pipes', fakeAsync(() => {
var el = createComp(
'<div [simpleDirective]="true | pipeNeedsChangeDetectorRef" directiveNeedsChangeDetectorRef></div>',