refactor(compiler): make `PLATFORM_PIPES` / `PLATFORM_DIRECTIVES` an option on `CompilerConfig`

This aligns the configuration of platform pipes / directives with offline compilation.

BREAKING CHANGE:
- `PLATFORM_PIPES` and `PLATFORM_DIRECTIVES` now are fields on `CompilerConfig`. 
  Instead of providing a binding to these tokens, provide a binding for `CompilerConfig` instead.
This commit is contained in:
Tobias Bosch 2016-06-13 08:35:31 -07:00
parent 1fb0db4aeb
commit 1745366530
9 changed files with 43 additions and 81 deletions

View File

@ -1,7 +1,7 @@
import {ViewEncapsulation} from '@angular/core'; import {ViewEncapsulation} from '@angular/core';
import {unimplemented} from '../src/facade/exceptions'; import {unimplemented} from '../src/facade/exceptions';
import {isBlank} from '../src/facade/lang'; import {Type, isBlank} from '../src/facade/lang';
import {CompileIdentifierMetadata} from './compile_metadata'; import {CompileIdentifierMetadata} from './compile_metadata';
import {Identifiers} from './identifiers'; import {Identifiers} from './identifiers';
@ -12,7 +12,8 @@ export class CompilerConfig {
constructor( constructor(
public genDebugInfo: boolean, public logBindingUpdate: boolean, public useJit: boolean, public genDebugInfo: boolean, public logBindingUpdate: boolean, public useJit: boolean,
renderTypes: RenderTypes = null, defaultEncapsulation: ViewEncapsulation = null) { renderTypes: RenderTypes = null, defaultEncapsulation: ViewEncapsulation = null,
public platformDirectives: any[] = [], public platformPipes: any[] = []) {
if (isBlank(renderTypes)) { if (isBlank(renderTypes)) {
renderTypes = new DefaultRenderTypes(); renderTypes = new DefaultRenderTypes();
} }

View File

@ -1,4 +1,4 @@
import {AnimationAnimateMetadata, AnimationEntryMetadata, AnimationGroupMetadata, AnimationKeyframesSequenceMetadata, AnimationMetadata, AnimationStateDeclarationMetadata, AnimationStateMetadata, AnimationStateTransitionMetadata, AnimationStyleMetadata, AnimationWithStepsMetadata, AttributeMetadata, ComponentMetadata, HostMetadata, Inject, InjectMetadata, Injectable, Optional, OptionalMetadata, PLATFORM_DIRECTIVES, PLATFORM_PIPES, Provider, QueryMetadata, SelfMetadata, SkipSelfMetadata, ViewMetadata, ViewQueryMetadata, resolveForwardRef} from '@angular/core'; import {AnimationAnimateMetadata, AnimationEntryMetadata, AnimationGroupMetadata, AnimationKeyframesSequenceMetadata, AnimationMetadata, AnimationStateDeclarationMetadata, AnimationStateMetadata, AnimationStateTransitionMetadata, AnimationStyleMetadata, AnimationWithStepsMetadata, AttributeMetadata, ComponentMetadata, HostMetadata, Inject, InjectMetadata, Injectable, Optional, OptionalMetadata, Provider, QueryMetadata, SelfMetadata, SkipSelfMetadata, ViewMetadata, ViewQueryMetadata, resolveForwardRef} from '@angular/core';
import {LIFECYCLE_HOOKS_VALUES, ReflectorReader, createProvider, isProviderLiteral, reflector} from '../core_private'; import {LIFECYCLE_HOOKS_VALUES, ReflectorReader, createProvider, isProviderLiteral, reflector} from '../core_private';
import {StringMapWrapper} from '../src/facade/collection'; import {StringMapWrapper} from '../src/facade/collection';
@ -7,6 +7,7 @@ import {Type, isArray, isBlank, isPresent, isString, isStringMap, stringify} fro
import {assertArrayOfStrings} from './assertions'; import {assertArrayOfStrings} from './assertions';
import * as cpl from './compile_metadata'; import * as cpl from './compile_metadata';
import {CompilerConfig} from './config';
import {hasLifecycleHook} from './directive_lifecycle_reflector'; import {hasLifecycleHook} from './directive_lifecycle_reflector';
import {DirectiveResolver} from './directive_resolver'; import {DirectiveResolver} from './directive_resolver';
import {PipeResolver} from './pipe_resolver'; import {PipeResolver} from './pipe_resolver';
@ -14,7 +15,6 @@ import {getUrlScheme} from './url_resolver';
import {MODULE_SUFFIX, ValueTransformer, sanitizeIdentifier, visitValue} from './util'; import {MODULE_SUFFIX, ValueTransformer, sanitizeIdentifier, visitValue} from './util';
import {ViewResolver} from './view_resolver'; import {ViewResolver} from './view_resolver';
@Injectable() @Injectable()
export class CompileMetadataResolver { export class CompileMetadataResolver {
private _directiveCache = new Map<Type, cpl.CompileDirectiveMetadata>(); private _directiveCache = new Map<Type, cpl.CompileDirectiveMetadata>();
@ -25,9 +25,7 @@ export class CompileMetadataResolver {
constructor( constructor(
private _directiveResolver: DirectiveResolver, private _pipeResolver: PipeResolver, private _directiveResolver: DirectiveResolver, private _pipeResolver: PipeResolver,
private _viewResolver: ViewResolver, private _viewResolver: ViewResolver, private _config: CompilerConfig,
@Optional() @Inject(PLATFORM_DIRECTIVES) private _platformDirectives: Type[],
@Optional() @Inject(PLATFORM_PIPES) private _platformPipes: Type[],
_reflector?: ReflectorReader) { _reflector?: ReflectorReader) {
if (isPresent(_reflector)) { if (isPresent(_reflector)) {
this._reflector = _reflector; this._reflector = _reflector;
@ -206,7 +204,7 @@ export class CompileMetadataResolver {
getViewDirectivesMetadata(component: Type): cpl.CompileDirectiveMetadata[] { getViewDirectivesMetadata(component: Type): cpl.CompileDirectiveMetadata[] {
var view = this._viewResolver.resolve(component); var view = this._viewResolver.resolve(component);
var directives = flattenDirectives(view, this._platformDirectives); var directives = flattenDirectives(view, this._config.platformDirectives);
for (var i = 0; i < directives.length; i++) { for (var i = 0; i < directives.length; i++) {
if (!isValidType(directives[i])) { if (!isValidType(directives[i])) {
throw new BaseException( throw new BaseException(
@ -218,7 +216,7 @@ export class CompileMetadataResolver {
getViewPipesMetadata(component: Type): cpl.CompilePipeMetadata[] { getViewPipesMetadata(component: Type): cpl.CompilePipeMetadata[] {
var view = this._viewResolver.resolve(component); var view = this._viewResolver.resolve(component);
var pipes = flattenPipes(view, this._platformPipes); var pipes = flattenPipes(view, this._config.platformPipes);
for (var i = 0; i < pipes.length; i++) { for (var i = 0; i < pipes.length; i++) {
if (!isValidType(pipes[i])) { if (!isValidType(pipes[i])) {
throw new BaseException( throw new BaseException(

View File

@ -7,7 +7,7 @@ import {CompileMetadataResolver} from '../src/metadata_resolver';
import {Component, Directive, ViewEncapsulation, ChangeDetectionStrategy, OnChanges, OnInit, DoCheck, OnDestroy, AfterContentInit, AfterContentChecked, AfterViewInit, AfterViewChecked, SimpleChanges,} from '@angular/core'; import {Component, Directive, ViewEncapsulation, ChangeDetectionStrategy, OnChanges, OnInit, DoCheck, OnDestroy, AfterContentInit, AfterContentChecked, AfterViewInit, AfterViewChecked, SimpleChanges,} from '@angular/core';
import {TEST_PROVIDERS} from './test_bindings'; import {TEST_PROVIDERS} from './test_bindings';
import {PLATFORM_DIRECTIVES} from '@angular/core/src/platform_directives_and_pipes'; import {CompilerConfig} from '@angular/compiler/src/config';
import {MalformedStylesComponent} from './metadata_resolver_fixture'; import {MalformedStylesComponent} from './metadata_resolver_fixture';
export function main() { export function main() {
@ -73,7 +73,10 @@ export function main() {
describe('platform directives', () => { describe('platform directives', () => {
beforeEachProviders( beforeEachProviders(
() => [{provide: PLATFORM_DIRECTIVES, useValue: [ADirective], multi: true}]); () => [{
provide: CompilerConfig,
useValue: new CompilerConfig(true, false, true, null, null, [ADirective])
}]);
it('should include platform directives when available', it('should include platform directives when available',
inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => { inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => {

View File

@ -21,7 +21,6 @@ export './src/core/debug/debug_node.dart' show DebugElement,
asNativeElements; asNativeElements;
export './src/core/testability/testability.dart'; export './src/core/testability/testability.dart';
export './src/core/change_detection.dart'; export './src/core/change_detection.dart';
export './src/core/platform_directives_and_pipes.dart';
export './src/core/platform_common_providers.dart'; export './src/core/platform_common_providers.dart';
export './src/core/application_common_providers.dart'; export './src/core/application_common_providers.dart';
export './src/core/reflection/reflection.dart'; export './src/core/reflection/reflection.dart';

View File

@ -14,7 +14,6 @@ export * from './src/linker';
export {DebugElement, DebugNode, asNativeElements, getDebugNode} from './src/debug/debug_node'; export {DebugElement, DebugNode, asNativeElements, getDebugNode} from './src/debug/debug_node';
export * from './src/testability/testability'; export * from './src/testability/testability';
export * from './src/change_detection'; export * from './src/change_detection';
export * from './src/platform_directives_and_pipes';
export * from './src/platform_common_providers'; export * from './src/platform_common_providers';
export * from './src/application_common_providers'; export * from './src/application_common_providers';
export {wtfCreateScope, wtfLeave, wtfStartTimeRange, wtfEndTimeRange, WtfScopeFn} from './src/profile/profile'; export {wtfCreateScope, wtfLeave, wtfStartTimeRange, wtfEndTimeRange, WtfScopeFn} from './src/profile/profile';

View File

@ -1,55 +0,0 @@
import {OpaqueToken} from './di';
/**
* A token that can be provided when bootstraping an application to make an array of directives
* available in every component of the application.
*
* ### Example
*
* ```typescript
* import {PLATFORM_DIRECTIVES} from '@angular/core';
* import {OtherDirective} from './myDirectives';
*
* @Component({
* selector: 'my-component',
* template: `
* <!-- can use other directive even though the component does not list it in `directives` -->
* <other-directive></other-directive>
* `
* })
* export class MyComponent {
* ...
* }
*
* bootstrap(MyComponent, [{provide: PLATFORM_DIRECTIVES, useValue: [OtherDirective], multi:true}]);
* ```
* @stable
*/
export const PLATFORM_DIRECTIVES: OpaqueToken =
/*@ts2dart_const*/ new OpaqueToken('Platform Directives');
/**
* A token that can be provided when bootstraping an application to make an array of pipes
* available in every component of the application.
*
* ### Example
*
* ```typescript
* import {PLATFORM_PIPES} from '@angular/core';
* import {OtherPipe} from './myPipe';
*
* @Component({
* selector: 'my-component',
* template: `
* {{123 | other-pipe}}
* `
* })
* export class MyComponent {
* ...
* }
*
* bootstrap(MyComponent, [{provide: PLATFORM_PIPES, useValue: [OtherPipe], multi:true}]);
* ```
* @stable
*/
export const PLATFORM_PIPES: OpaqueToken = /*@ts2dart_const*/ new OpaqueToken('Platform Pipes');

View File

@ -4,7 +4,7 @@ import {AsyncTestCompleter} from '@angular/core/testing/testing_internal';
import {IS_DART} from '../../src/facade/lang'; import {IS_DART} from '../../src/facade/lang';
import {Component, Pipe, PipeTransform, provide, ViewMetadata, PLATFORM_PIPES, OpaqueToken, Injector} from '@angular/core'; import {Component, Pipe, PipeTransform, provide, ViewMetadata, OpaqueToken, Injector} from '@angular/core';
import {NgIf, NgClass} from '@angular/common'; import {NgIf, NgClass} from '@angular/common';
import {CompilerConfig} from '@angular/compiler'; import {CompilerConfig} from '@angular/compiler';
@ -31,7 +31,11 @@ function declareTests(isJit: boolean) {
describe('regressions', () => { describe('regressions', () => {
describe('platform pipes', () => { describe('platform pipes', () => {
beforeEachProviders(() => [{provide: PLATFORM_PIPES, useValue: [PlatformPipe], multi: true}]); beforeEachProviders(
() => [{
provide: CompilerConfig,
useValue: new CompilerConfig(true, false, isJit, null, null, [PlatformPipe])
}]);
it('should overwrite them by custom pipes', it('should overwrite them by custom pipes',
inject( inject(

View File

@ -1,6 +1,6 @@
import {COMMON_DIRECTIVES, COMMON_PIPES, FORM_PROVIDERS, PlatformLocation} from '@angular/common'; import {COMMON_DIRECTIVES, COMMON_PIPES, FORM_PROVIDERS, PlatformLocation} from '@angular/common';
import {COMPILER_PROVIDERS, XHR} from '@angular/compiler'; import {COMPILER_PROVIDERS, CompilerConfig, XHR} from '@angular/compiler';
import {APPLICATION_COMMON_PROVIDERS, ComponentRef, ExceptionHandler, OpaqueToken, PLATFORM_COMMON_PROVIDERS, PLATFORM_DIRECTIVES, PLATFORM_INITIALIZER, PLATFORM_PIPES, PlatformRef, ReflectiveInjector, RootRenderer, Testability, Type, assertPlatform, coreLoadAndBootstrap, createPlatform, getPlatform} from '@angular/core'; import {APPLICATION_COMMON_PROVIDERS, ComponentRef, ExceptionHandler, OpaqueToken, PLATFORM_COMMON_PROVIDERS, PLATFORM_INITIALIZER, PlatformRef, ReflectiveInjector, RootRenderer, Testability, Type, assertPlatform, coreLoadAndBootstrap, createPlatform, getPlatform} from '@angular/core';
import {AnimationDriver, NoOpAnimationDriver, ReflectionCapabilities, SanitizationService, reflector, wtfInit} from '../core_private'; import {AnimationDriver, NoOpAnimationDriver, ReflectionCapabilities, SanitizationService, reflector, wtfInit} from '../core_private';
import {WebAnimationsDriver} from '../src/dom/web_animations_driver'; import {WebAnimationsDriver} from '../src/dom/web_animations_driver';
@ -17,7 +17,7 @@ import {EVENT_MANAGER_PLUGINS, EventManager} from './dom/events/event_manager';
import {HAMMER_GESTURE_CONFIG, HammerGestureConfig, HammerGesturesPlugin} from './dom/events/hammer_gestures'; import {HAMMER_GESTURE_CONFIG, HammerGestureConfig, HammerGesturesPlugin} from './dom/events/hammer_gestures';
import {KeyEventsPlugin} from './dom/events/key_events'; import {KeyEventsPlugin} from './dom/events/key_events';
import {DomSharedStylesHost, SharedStylesHost} from './dom/shared_styles_host'; import {DomSharedStylesHost, SharedStylesHost} from './dom/shared_styles_host';
import {isBlank, isPresent} from './facade/lang'; import {assertionsEnabled, isBlank, isPresent} from './facade/lang';
import {DomSanitizationService, DomSanitizationServiceImpl} from './security/dom_sanitization_service'; import {DomSanitizationService, DomSanitizationServiceImpl} from './security/dom_sanitization_service';
import {CachedXHR} from './xhr/xhr_cache'; import {CachedXHR} from './xhr/xhr_cache';
import {XHRImpl} from './xhr/xhr_impl'; import {XHRImpl} from './xhr/xhr_impl';
@ -50,8 +50,6 @@ export const BROWSER_SANITIZATION_PROVIDERS: Array<any> = [
*/ */
export const BROWSER_APP_PROVIDERS: Array<any /*Type | Provider | any[]*/> = [ export const BROWSER_APP_PROVIDERS: Array<any /*Type | Provider | any[]*/> = [
APPLICATION_COMMON_PROVIDERS, FORM_PROVIDERS, BROWSER_SANITIZATION_PROVIDERS, APPLICATION_COMMON_PROVIDERS, FORM_PROVIDERS, BROWSER_SANITIZATION_PROVIDERS,
{provide: PLATFORM_PIPES, useValue: COMMON_PIPES, multi: true},
{provide: PLATFORM_DIRECTIVES, useValue: COMMON_DIRECTIVES, multi: true},
{provide: ExceptionHandler, useFactory: _exceptionHandler, deps: []}, {provide: ExceptionHandler, useFactory: _exceptionHandler, deps: []},
{provide: DOCUMENT, useFactory: _document, deps: []}, {provide: DOCUMENT, useFactory: _document, deps: []},
{provide: EVENT_MANAGER_PLUGINS, useClass: DomEventsPlugin, multi: true}, {provide: EVENT_MANAGER_PLUGINS, useClass: DomEventsPlugin, multi: true},
@ -65,8 +63,14 @@ export const BROWSER_APP_PROVIDERS: Array<any /*Type | Provider | any[]*/> = [
Testability, EventManager, ELEMENT_PROBE_PROVIDERS Testability, EventManager, ELEMENT_PROBE_PROVIDERS
]; ];
function _createCompilerConfig() {
return new CompilerConfig(
assertionsEnabled(), false, true, null, null, COMMON_DIRECTIVES, COMMON_PIPES);
}
export const BROWSER_APP_COMPILER_PROVIDERS: Array<any /*Type | Provider | any[]*/> = [ export const BROWSER_APP_COMPILER_PROVIDERS: Array<any /*Type | Provider | any[]*/> = [
COMPILER_PROVIDERS, COMPILER_PROVIDERS,
{provide: CompilerConfig, useFactory: _createCompilerConfig, deps: []},
{provide: XHR, useClass: XHRImpl}, {provide: XHR, useClass: XHRImpl},
]; ];

View File

@ -1,9 +1,9 @@
import {COMMON_DIRECTIVES, COMMON_PIPES, FORM_PROVIDERS} from '@angular/common'; import {COMMON_DIRECTIVES, COMMON_PIPES, FORM_PROVIDERS} from '@angular/common';
import {COMPILER_PROVIDERS, XHR} from '@angular/compiler'; import {COMPILER_PROVIDERS, CompilerConfig, XHR} from '@angular/compiler';
import {APPLICATION_COMMON_PROVIDERS, APP_INITIALIZER, ComponentRef, ExceptionHandler, NgZone, OpaqueToken, PLATFORM_COMMON_PROVIDERS, PLATFORM_DIRECTIVES, PLATFORM_PIPES, PlatformRef, ReflectiveInjector, RootRenderer, Type, assertPlatform, coreLoadAndBootstrap, createPlatform, getPlatform} from '@angular/core'; import {APPLICATION_COMMON_PROVIDERS, APP_INITIALIZER, ComponentRef, ExceptionHandler, NgZone, OpaqueToken, PLATFORM_COMMON_PROVIDERS, PlatformRef, ReflectiveInjector, RootRenderer, Type, assertPlatform, coreLoadAndBootstrap, createPlatform, getPlatform} from '@angular/core';
import {BROWSER_SANITIZATION_PROVIDERS} from './browser'; import {BROWSER_SANITIZATION_PROVIDERS} from './browser';
import {isBlank, isPresent, print} from './facade/lang'; import {assertionsEnabled, isBlank, isPresent, print} from './facade/lang';
import {ON_WEB_WORKER} from './web_workers/shared/api'; import {ON_WEB_WORKER} from './web_workers/shared/api';
import {ClientMessageBrokerFactory, ClientMessageBrokerFactory_} from './web_workers/shared/client_message_broker'; import {ClientMessageBrokerFactory, ClientMessageBrokerFactory_} from './web_workers/shared/client_message_broker';
import {MessageBus} from './web_workers/shared/message_bus'; import {MessageBus} from './web_workers/shared/message_bus';
@ -29,8 +29,6 @@ export const WORKER_APP_PLATFORM_PROVIDERS: Array<any /*Type | Provider | any[]*
export const WORKER_APP_APPLICATION_PROVIDERS: Array<any /*Type | Provider | any[]*/> = [ export const WORKER_APP_APPLICATION_PROVIDERS: Array<any /*Type | Provider | any[]*/> = [
APPLICATION_COMMON_PROVIDERS, FORM_PROVIDERS, BROWSER_SANITIZATION_PROVIDERS, Serializer, APPLICATION_COMMON_PROVIDERS, FORM_PROVIDERS, BROWSER_SANITIZATION_PROVIDERS, Serializer,
{provide: PLATFORM_PIPES, useValue: COMMON_PIPES, multi: true},
{provide: PLATFORM_DIRECTIVES, useValue: COMMON_DIRECTIVES, multi: true},
{provide: ClientMessageBrokerFactory, useClass: ClientMessageBrokerFactory_}, {provide: ClientMessageBrokerFactory, useClass: ClientMessageBrokerFactory_},
{provide: ServiceMessageBrokerFactory, useClass: ServiceMessageBrokerFactory_}, {provide: ServiceMessageBrokerFactory, useClass: ServiceMessageBrokerFactory_},
WebWorkerRootRenderer, {provide: RootRenderer, useExisting: WebWorkerRootRenderer}, WebWorkerRootRenderer, {provide: RootRenderer, useExisting: WebWorkerRootRenderer},
@ -47,12 +45,23 @@ export function workerAppPlatform(): PlatformRef {
return assertPlatform(WORKER_APP_PLATFORM_MARKER); return assertPlatform(WORKER_APP_PLATFORM_MARKER);
} }
function _createCompilerConfig() {
return new CompilerConfig(
assertionsEnabled(), false, true, null, null, COMMON_DIRECTIVES, COMMON_PIPES);
}
export const WORKER_APP_COMPILER_PROVIDERS: Array<any /*Type | Provider | any[]*/> = [
COMPILER_PROVIDERS,
{provide: CompilerConfig, useFactory: _createCompilerConfig, deps: []},
{provide: XHR, useClass: XHRImpl},
];
export function bootstrapApp( export function bootstrapApp(
appComponentType: Type, appComponentType: Type,
customProviders?: Array<any /*Type | Provider | any[]*/>): Promise<ComponentRef<any>> { customProviders?: Array<any /*Type | Provider | any[]*/>): Promise<ComponentRef<any>> {
var appInjector = ReflectiveInjector.resolveAndCreate( var appInjector = ReflectiveInjector.resolveAndCreate(
[ [
WORKER_APP_APPLICATION_PROVIDERS, COMPILER_PROVIDERS, {provide: XHR, useClass: XHRImpl}, WORKER_APP_APPLICATION_PROVIDERS, WORKER_APP_COMPILER_PROVIDERS,
isPresent(customProviders) ? customProviders : [] isPresent(customProviders) ? customProviders : []
], ],
workerAppPlatform().injector); workerAppPlatform().injector);