fix(compiler): Update types for TypeScript nullability support
This commit is contained in:
parent
d8b73e4223
commit
09d9f5fe54
@ -33,7 +33,7 @@ export class CompilerHost implements AotCompilerHost {
|
|||||||
private resolverCache = new Map<string, ModuleMetadata[]>();
|
private resolverCache = new Map<string, ModuleMetadata[]>();
|
||||||
private bundleIndexCache = new Map<string, boolean>();
|
private bundleIndexCache = new Map<string, boolean>();
|
||||||
private bundleIndexNames = new Set<string>();
|
private bundleIndexNames = new Set<string>();
|
||||||
private moduleFileNames = new Map<string, string>();
|
private moduleFileNames = new Map<string, string|null>();
|
||||||
protected resolveModuleNameHost: CompilerHostContext;
|
protected resolveModuleNameHost: CompilerHostContext;
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
@ -71,7 +71,7 @@ export class CompilerHost implements AotCompilerHost {
|
|||||||
|
|
||||||
moduleNameToFileName(m: string, containingFile: string): string|null {
|
moduleNameToFileName(m: string, containingFile: string): string|null {
|
||||||
const key = m + ':' + (containingFile || '');
|
const key = m + ':' + (containingFile || '');
|
||||||
let result = this.moduleFileNames.get(key);
|
let result: string|null = this.moduleFileNames.get(key) || null;
|
||||||
if (!result) {
|
if (!result) {
|
||||||
if (!containingFile || !containingFile.length) {
|
if (!containingFile || !containingFile.length) {
|
||||||
if (m.indexOf('.') === 0) {
|
if (m.indexOf('.') === 0) {
|
||||||
@ -183,7 +183,7 @@ export class CompilerHost implements AotCompilerHost {
|
|||||||
return sf;
|
return sf;
|
||||||
}
|
}
|
||||||
|
|
||||||
getMetadataFor(filePath: string): ModuleMetadata[] {
|
getMetadataFor(filePath: string): ModuleMetadata[]|undefined {
|
||||||
if (!this.context.fileExists(filePath)) {
|
if (!this.context.fileExists(filePath)) {
|
||||||
// If the file doesn't exists then we cannot return metadata for the file.
|
// If the file doesn't exists then we cannot return metadata for the file.
|
||||||
// This will occur if the user refernced a declared module for which no file
|
// This will occur if the user refernced a declared module for which no file
|
||||||
@ -263,6 +263,7 @@ export class CompilerHost implements AotCompilerHost {
|
|||||||
if (this.context.fileExists(filePath)) {
|
if (this.context.fileExists(filePath)) {
|
||||||
return this.context.readFile(filePath);
|
return this.context.readFile(filePath);
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
getOutputFileName(sourceFilePath: string): string {
|
getOutputFileName(sourceFilePath: string): string {
|
||||||
@ -287,7 +288,7 @@ export class CompilerHost implements AotCompilerHost {
|
|||||||
|
|
||||||
calculateEmitPath(filePath: string): string {
|
calculateEmitPath(filePath: string): string {
|
||||||
// Write codegen in a directory structure matching the sources.
|
// Write codegen in a directory structure matching the sources.
|
||||||
let root = this.options.basePath;
|
let root = this.options.basePath !;
|
||||||
for (const eachRootDir of this.options.rootDirs || []) {
|
for (const eachRootDir of this.options.rootDirs || []) {
|
||||||
if (this.options.trace) {
|
if (this.options.trace) {
|
||||||
console.error(`Check if ${filePath} is under rootDirs element ${eachRootDir}`);
|
console.error(`Check if ${filePath} is under rootDirs element ${eachRootDir}`);
|
||||||
@ -373,7 +374,7 @@ export class ModuleResolutionHostAdapter extends CompilerHostContextAdapter impl
|
|||||||
constructor(private host: ts.ModuleResolutionHost) {
|
constructor(private host: ts.ModuleResolutionHost) {
|
||||||
super();
|
super();
|
||||||
if (host.directoryExists) {
|
if (host.directoryExists) {
|
||||||
this.directoryExists = (directoryName: string) => host.directoryExists(directoryName);
|
this.directoryExists = (directoryName: string) => host.directoryExists !(directoryName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -23,7 +23,7 @@ function extract(
|
|||||||
ngOptions: tsc.AngularCompilerOptions, cliOptions: tsc.I18nExtractionCliOptions,
|
ngOptions: tsc.AngularCompilerOptions, cliOptions: tsc.I18nExtractionCliOptions,
|
||||||
program: ts.Program, host: ts.CompilerHost): Promise<void> {
|
program: ts.Program, host: ts.CompilerHost): Promise<void> {
|
||||||
return Extractor.create(ngOptions, program, host, cliOptions.locale)
|
return Extractor.create(ngOptions, program, host, cliOptions.locale)
|
||||||
.extract(cliOptions.i18nFormat, cliOptions.outFile);
|
.extract(cliOptions.i18nFormat !, cliOptions.outFile);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Entry point
|
// Entry point
|
||||||
|
@ -92,9 +92,9 @@ export class NgTools_InternalApi_NG_2 {
|
|||||||
const hostContext: CompilerHostContext =
|
const hostContext: CompilerHostContext =
|
||||||
new CustomLoaderModuleResolutionHostAdapter(options.readResource, options.host);
|
new CustomLoaderModuleResolutionHostAdapter(options.readResource, options.host);
|
||||||
const cliOptions: NgcCliOptions = {
|
const cliOptions: NgcCliOptions = {
|
||||||
i18nFormat: options.i18nFormat,
|
i18nFormat: options.i18nFormat !,
|
||||||
i18nFile: options.i18nFile,
|
i18nFile: options.i18nFile !,
|
||||||
locale: options.locale,
|
locale: options.locale !,
|
||||||
basePath: options.basePath
|
basePath: options.basePath
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -148,6 +148,6 @@ export class NgTools_InternalApi_NG_2 {
|
|||||||
const extractor = Extractor.create(
|
const extractor = Extractor.create(
|
||||||
options.angularCompilerOptions, options.program, options.host, locale, hostContext);
|
options.angularCompilerOptions, options.program, options.host, locale, hostContext);
|
||||||
|
|
||||||
return extractor.extract(options.i18nFormat, options.outFile || null);
|
return extractor.extract(options.i18nFormat !, options.outFile || null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -33,7 +33,8 @@ export type LazyRouteMap = {
|
|||||||
// A route definition. Normally the short form 'path/to/module#ModuleClassName' is used by
|
// A route definition. Normally the short form 'path/to/module#ModuleClassName' is used by
|
||||||
// the user, and this is a helper class to extract information from it.
|
// the user, and this is a helper class to extract information from it.
|
||||||
export class RouteDef {
|
export class RouteDef {
|
||||||
private constructor(public readonly path: string, public readonly className: string = null) {}
|
private constructor(public readonly path: string, public readonly className: string|null = null) {
|
||||||
|
}
|
||||||
|
|
||||||
toString() {
|
toString() {
|
||||||
return (this.className === null || this.className == 'default') ?
|
return (this.className === null || this.className == 'default') ?
|
||||||
@ -58,7 +59,7 @@ export function listLazyRoutesOfModule(
|
|||||||
const entryRouteDef = RouteDef.fromString(entryModule);
|
const entryRouteDef = RouteDef.fromString(entryModule);
|
||||||
const containingFile = _resolveModule(entryRouteDef.path, entryRouteDef.path, host);
|
const containingFile = _resolveModule(entryRouteDef.path, entryRouteDef.path, host);
|
||||||
const modulePath = `./${containingFile.replace(/^(.*)\//, '')}`;
|
const modulePath = `./${containingFile.replace(/^(.*)\//, '')}`;
|
||||||
const className = entryRouteDef.className;
|
const className = entryRouteDef.className !;
|
||||||
|
|
||||||
// List loadChildren of this single module.
|
// List loadChildren of this single module.
|
||||||
const appStaticSymbol = reflector.findDeclaration(modulePath, className, containingFile);
|
const appStaticSymbol = reflector.findDeclaration(modulePath, className, containingFile);
|
||||||
|
@ -40,7 +40,7 @@ export class PathMappedCompilerHost extends CompilerHost {
|
|||||||
return fileName;
|
return fileName;
|
||||||
}
|
}
|
||||||
|
|
||||||
moduleNameToFileName(m: string, containingFile: string) {
|
moduleNameToFileName(m: string, containingFile: string): string|null {
|
||||||
if (!containingFile || !containingFile.length) {
|
if (!containingFile || !containingFile.length) {
|
||||||
if (m.indexOf('.') === 0) {
|
if (m.indexOf('.') === 0) {
|
||||||
throw new Error('Resolution of relative paths requires a containing file.');
|
throw new Error('Resolution of relative paths requires a containing file.');
|
||||||
@ -59,6 +59,7 @@ export class PathMappedCompilerHost extends CompilerHost {
|
|||||||
return this.getCanonicalFileName(resolved.resolvedFileName);
|
return this.getCanonicalFileName(resolved.resolvedFileName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -90,7 +91,7 @@ export class PathMappedCompilerHost extends CompilerHost {
|
|||||||
|
|
||||||
const importModuleName = importedFile.replace(EXT, '');
|
const importModuleName = importedFile.replace(EXT, '');
|
||||||
const parts = importModuleName.split(path.sep).filter(p => !!p);
|
const parts = importModuleName.split(path.sep).filter(p => !!p);
|
||||||
let foundRelativeImport: string;
|
let foundRelativeImport: string = undefined !;
|
||||||
for (let index = parts.length - 1; index >= 0; index--) {
|
for (let index = parts.length - 1; index >= 0; index--) {
|
||||||
let candidate = parts.slice(index, parts.length).join(path.sep);
|
let candidate = parts.slice(index, parts.length).join(path.sep);
|
||||||
if (resolvable(candidate)) {
|
if (resolvable(candidate)) {
|
||||||
@ -135,5 +136,6 @@ export class PathMappedCompilerHost extends CompilerHost {
|
|||||||
return metadata ? [metadata] : [];
|
return metadata ? [metadata] : [];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return null !;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
"declaration": true,
|
"declaration": true,
|
||||||
"experimentalDecorators": true,
|
"experimentalDecorators": true,
|
||||||
"noImplicitAny": true,
|
"noImplicitAny": true,
|
||||||
|
"strictNullChecks": true,
|
||||||
"module": "commonjs",
|
"module": "commonjs",
|
||||||
"outDir": "../../dist/packages/compiler-cli",
|
"outDir": "../../dist/packages/compiler-cli",
|
||||||
"paths": {
|
"paths": {
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
* found in the LICENSE file at https://angular.io/license
|
* found in the LICENSE file at https://angular.io/license
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import {CompileDirectiveMetadata, CompileIdentifierMetadata, CompileNgModuleMetadata, CompileProviderMetadata, componentFactoryName, createHostComponentMeta, flatten, identifierName, sourceUrl, templateSourceUrl} from '../compile_metadata';
|
import {CompileDirectiveMetadata, CompileIdentifierMetadata, CompileNgModuleMetadata, CompileProviderMetadata, CompileTypeSummary, componentFactoryName, createHostComponentMeta, flatten, identifierName, sourceUrl, templateSourceUrl} from '../compile_metadata';
|
||||||
import {CompilerConfig} from '../config';
|
import {CompilerConfig} from '../config';
|
||||||
import {Identifiers, createIdentifier, createIdentifierToken} from '../identifiers';
|
import {Identifiers, createIdentifier, createIdentifierToken} from '../identifiers';
|
||||||
import {CompileMetadataResolver} from '../metadata_resolver';
|
import {CompileMetadataResolver} from '../metadata_resolver';
|
||||||
@ -32,8 +32,8 @@ export class AotCompiler {
|
|||||||
private _metadataResolver: CompileMetadataResolver, private _templateParser: TemplateParser,
|
private _metadataResolver: CompileMetadataResolver, private _templateParser: TemplateParser,
|
||||||
private _styleCompiler: StyleCompiler, private _viewCompiler: ViewCompiler,
|
private _styleCompiler: StyleCompiler, private _viewCompiler: ViewCompiler,
|
||||||
private _ngModuleCompiler: NgModuleCompiler, private _outputEmitter: OutputEmitter,
|
private _ngModuleCompiler: NgModuleCompiler, private _outputEmitter: OutputEmitter,
|
||||||
private _summaryResolver: SummaryResolver<StaticSymbol>, private _localeId: string,
|
private _summaryResolver: SummaryResolver<StaticSymbol>, private _localeId: string|null,
|
||||||
private _translationFormat: string, private _genFilePreamble: string,
|
private _translationFormat: string|null, private _genFilePreamble: string|null,
|
||||||
private _symbolResolver: StaticSymbolResolver) {}
|
private _symbolResolver: StaticSymbolResolver) {}
|
||||||
|
|
||||||
clearCache() { this._metadataResolver.clearCache(); }
|
clearCache() { this._metadataResolver.clearCache(); }
|
||||||
@ -113,11 +113,11 @@ export class AotCompiler {
|
|||||||
targetExportedVars: string[]): GeneratedFile {
|
targetExportedVars: string[]): GeneratedFile {
|
||||||
const symbolSummaries = this._symbolResolver.getSymbolsOf(srcFileUrl)
|
const symbolSummaries = this._symbolResolver.getSymbolsOf(srcFileUrl)
|
||||||
.map(symbol => this._symbolResolver.resolveSymbol(symbol));
|
.map(symbol => this._symbolResolver.resolveSymbol(symbol));
|
||||||
const typeSummaries = [
|
const typeSummaries: CompileTypeSummary[] = [
|
||||||
...ngModules.map(ref => this._metadataResolver.getNgModuleSummary(ref)),
|
...ngModules.map(ref => this._metadataResolver.getNgModuleSummary(ref) !),
|
||||||
...directives.map(ref => this._metadataResolver.getDirectiveSummary(ref)),
|
...directives.map(ref => this._metadataResolver.getDirectiveSummary(ref) !),
|
||||||
...pipes.map(ref => this._metadataResolver.getPipeSummary(ref)),
|
...pipes.map(ref => this._metadataResolver.getPipeSummary(ref) !),
|
||||||
...injectables.map(ref => this._metadataResolver.getInjectableSummary(ref))
|
...injectables.map(ref => this._metadataResolver.getInjectableSummary(ref) !)
|
||||||
];
|
];
|
||||||
const {json, exportAs} = serializeSummaries(
|
const {json, exportAs} = serializeSummaries(
|
||||||
this._summaryResolver, this._symbolResolver, symbolSummaries, typeSummaries);
|
this._summaryResolver, this._symbolResolver, symbolSummaries, typeSummaries);
|
||||||
@ -130,7 +130,7 @@ export class AotCompiler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private _compileModule(ngModuleType: StaticSymbol, targetStatements: o.Statement[]): string {
|
private _compileModule(ngModuleType: StaticSymbol, targetStatements: o.Statement[]): string {
|
||||||
const ngModule = this._metadataResolver.getNgModuleMetadata(ngModuleType);
|
const ngModule = this._metadataResolver.getNgModuleMetadata(ngModuleType) !;
|
||||||
const providers: CompileProviderMetadata[] = [];
|
const providers: CompileProviderMetadata[] = [];
|
||||||
|
|
||||||
if (this._localeId) {
|
if (this._localeId) {
|
||||||
@ -183,11 +183,11 @@ export class AotCompiler {
|
|||||||
o.variable(hostViewFactoryVar), new o.LiteralMapExpr(inputsExprs),
|
o.variable(hostViewFactoryVar), new o.LiteralMapExpr(inputsExprs),
|
||||||
new o.LiteralMapExpr(outputsExprs),
|
new o.LiteralMapExpr(outputsExprs),
|
||||||
o.literalArr(
|
o.literalArr(
|
||||||
compMeta.template.ngContentSelectors.map(selector => o.literal(selector)))
|
compMeta.template !.ngContentSelectors.map(selector => o.literal(selector)))
|
||||||
]))
|
]))
|
||||||
.toDeclStmt(
|
.toDeclStmt(
|
||||||
o.importType(
|
o.importType(
|
||||||
createIdentifier(Identifiers.ComponentFactory), [o.importType(compMeta.type)],
|
createIdentifier(Identifiers.ComponentFactory), [o.importType(compMeta.type) !],
|
||||||
[o.TypeModifier.Const]),
|
[o.TypeModifier.Const]),
|
||||||
[o.StmtModifier.Final]));
|
[o.StmtModifier.Final]));
|
||||||
return compFactoryVar;
|
return compFactoryVar;
|
||||||
@ -195,7 +195,7 @@ export class AotCompiler {
|
|||||||
|
|
||||||
private _compileComponent(
|
private _compileComponent(
|
||||||
compMeta: CompileDirectiveMetadata, ngModule: CompileNgModuleMetadata,
|
compMeta: CompileDirectiveMetadata, ngModule: CompileNgModuleMetadata,
|
||||||
directiveIdentifiers: CompileIdentifierMetadata[], componentStyles: CompiledStylesheet,
|
directiveIdentifiers: CompileIdentifierMetadata[], componentStyles: CompiledStylesheet|null,
|
||||||
fileSuffix: string,
|
fileSuffix: string,
|
||||||
targetStatements: o.Statement[]): {viewClassVar: string, compRenderTypeVar: string} {
|
targetStatements: o.Statement[]): {viewClassVar: string, compRenderTypeVar: string} {
|
||||||
const directives =
|
const directives =
|
||||||
@ -204,8 +204,8 @@ export class AotCompiler {
|
|||||||
pipe => this._metadataResolver.getPipeSummary(pipe.reference));
|
pipe => this._metadataResolver.getPipeSummary(pipe.reference));
|
||||||
|
|
||||||
const {template: parsedTemplate, pipes: usedPipes} = this._templateParser.parse(
|
const {template: parsedTemplate, pipes: usedPipes} = this._templateParser.parse(
|
||||||
compMeta, compMeta.template.template, directives, pipes, ngModule.schemas,
|
compMeta, compMeta.template !.template !, directives, pipes, ngModule.schemas,
|
||||||
templateSourceUrl(ngModule.type, compMeta, compMeta.template));
|
templateSourceUrl(ngModule.type, compMeta, compMeta.template !));
|
||||||
const stylesExpr = componentStyles ? o.variable(componentStyles.stylesVar) : o.literalArr([]);
|
const stylesExpr = componentStyles ? o.variable(componentStyles.stylesVar) : o.literalArr([]);
|
||||||
const viewResult =
|
const viewResult =
|
||||||
this._viewCompiler.compileComponent(compMeta, parsedTemplate, stylesExpr, usedPipes);
|
this._viewCompiler.compileComponent(compMeta, parsedTemplate, stylesExpr, usedPipes);
|
||||||
@ -221,8 +221,9 @@ export class AotCompiler {
|
|||||||
fileUrl: string, stylesCompileResult: CompiledStylesheet, fileSuffix: string): GeneratedFile {
|
fileUrl: string, stylesCompileResult: CompiledStylesheet, fileSuffix: string): GeneratedFile {
|
||||||
_resolveStyleStatements(this._symbolResolver, stylesCompileResult, fileSuffix);
|
_resolveStyleStatements(this._symbolResolver, stylesCompileResult, fileSuffix);
|
||||||
return this._codegenSourceModule(
|
return this._codegenSourceModule(
|
||||||
fileUrl, _stylesModuleUrl(
|
fileUrl,
|
||||||
stylesCompileResult.meta.moduleUrl, stylesCompileResult.isShimmed, fileSuffix),
|
_stylesModuleUrl(
|
||||||
|
stylesCompileResult.meta.moduleUrl !, stylesCompileResult.isShimmed, fileSuffix),
|
||||||
stylesCompileResult.statements, [stylesCompileResult.stylesVar]);
|
stylesCompileResult.statements, [stylesCompileResult.stylesVar]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -70,15 +70,16 @@ export function createAotCompiler(compilerHost: AotCompilerHost, options: AotCom
|
|||||||
console, symbolCache, staticReflector);
|
console, symbolCache, staticReflector);
|
||||||
// TODO(vicb): do not pass options.i18nFormat here
|
// TODO(vicb): do not pass options.i18nFormat here
|
||||||
const importResolver = {
|
const importResolver = {
|
||||||
getImportAs: (symbol: StaticSymbol) => symbolResolver.getImportAs(symbol),
|
getImportAs: (symbol: StaticSymbol) => symbolResolver.getImportAs(symbol) !,
|
||||||
fileNameToModuleName: (fileName: string, containingFilePath: string) =>
|
fileNameToModuleName: (fileName: string, containingFilePath: string) =>
|
||||||
compilerHost.fileNameToModuleName(fileName, containingFilePath),
|
compilerHost.fileNameToModuleName(fileName, containingFilePath),
|
||||||
getTypeArity: (symbol: StaticSymbol) => symbolResolver.getTypeArity(symbol)
|
getTypeArity: (symbol: StaticSymbol) => symbolResolver.getTypeArity(symbol) !
|
||||||
};
|
};
|
||||||
const viewCompiler = new ViewCompiler(config, elementSchemaRegistry);
|
const viewCompiler = new ViewCompiler(config, elementSchemaRegistry);
|
||||||
const compiler = new AotCompiler(
|
const compiler = new AotCompiler(
|
||||||
config, compilerHost, resolver, tmplParser, new StyleCompiler(urlResolver), viewCompiler,
|
config, compilerHost, resolver, tmplParser, new StyleCompiler(urlResolver), viewCompiler,
|
||||||
new NgModuleCompiler(), new TypeScriptEmitter(importResolver), summaryResolver,
|
new NgModuleCompiler(), new TypeScriptEmitter(importResolver), summaryResolver,
|
||||||
options.locale, options.i18nFormat, options.genFilePreamble, symbolResolver);
|
options.locale || null, options.i18nFormat || null, options.genFilePreamble || null,
|
||||||
|
symbolResolver);
|
||||||
return {compiler, reflector: staticReflector};
|
return {compiler, reflector: staticReflector};
|
||||||
}
|
}
|
||||||
|
@ -20,8 +20,7 @@ export interface AotCompilerHost extends StaticSymbolResolverHost, AotSummaryRes
|
|||||||
*
|
*
|
||||||
* See ImportResolver.
|
* See ImportResolver.
|
||||||
*/
|
*/
|
||||||
fileNameToModuleName(importedFilePath: string, containingFilePath: string): string
|
fileNameToModuleName(importedFilePath: string, containingFilePath: string): string|null;
|
||||||
/*|null*/;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Loads a resource (e.g. html / css)
|
* Loads a resource (e.g. html / css)
|
||||||
|
@ -41,7 +41,7 @@ export class StaticAndDynamicReflectionCapabilities {
|
|||||||
getter(name: string): ɵGetterFn { return this.dynamicDelegate.getter(name); }
|
getter(name: string): ɵGetterFn { return this.dynamicDelegate.getter(name); }
|
||||||
setter(name: string): ɵSetterFn { return this.dynamicDelegate.setter(name); }
|
setter(name: string): ɵSetterFn { return this.dynamicDelegate.setter(name); }
|
||||||
method(name: string): ɵMethodFn { return this.dynamicDelegate.method(name); }
|
method(name: string): ɵMethodFn { return this.dynamicDelegate.method(name); }
|
||||||
importUri(type: any): string { return this.staticDelegate.importUri(type); }
|
importUri(type: any): string { return this.staticDelegate.importUri(type) !; }
|
||||||
resourceUri(type: any): string { return this.staticDelegate.resourceUri(type); }
|
resourceUri(type: any): string { return this.staticDelegate.resourceUri(type); }
|
||||||
resolveIdentifier(name: string, moduleUrl: string, members: string[], runtime: any) {
|
resolveIdentifier(name: string, moduleUrl: string, members: string[], runtime: any) {
|
||||||
return this.staticDelegate.resolveIdentifier(name, moduleUrl, members);
|
return this.staticDelegate.resolveIdentifier(name, moduleUrl, members);
|
||||||
|
@ -47,7 +47,7 @@ export class StaticReflector implements ɵReflectorReader {
|
|||||||
private symbolResolver: StaticSymbolResolver,
|
private symbolResolver: StaticSymbolResolver,
|
||||||
knownMetadataClasses: {name: string, filePath: string, ctor: any}[] = [],
|
knownMetadataClasses: {name: string, filePath: string, ctor: any}[] = [],
|
||||||
knownMetadataFunctions: {name: string, filePath: string, fn: any}[] = [],
|
knownMetadataFunctions: {name: string, filePath: string, fn: any}[] = [],
|
||||||
private errorRecorder?: (error: any, fileName: string) => void) {
|
private errorRecorder?: (error: any, fileName?: string) => void) {
|
||||||
this.initializeConversionMap();
|
this.initializeConversionMap();
|
||||||
knownMetadataClasses.forEach(
|
knownMetadataClasses.forEach(
|
||||||
(kc) => this._registerDecoratorOrConstructor(
|
(kc) => this._registerDecoratorOrConstructor(
|
||||||
@ -67,7 +67,7 @@ export class StaticReflector implements ɵReflectorReader {
|
|||||||
this.annotationNames.set(Injectable, 'Injectable');
|
this.annotationNames.set(Injectable, 'Injectable');
|
||||||
}
|
}
|
||||||
|
|
||||||
importUri(typeOrFunc: StaticSymbol): string {
|
importUri(typeOrFunc: StaticSymbol): string|null {
|
||||||
const staticSymbol = this.findSymbolDeclaration(typeOrFunc);
|
const staticSymbol = this.findSymbolDeclaration(typeOrFunc);
|
||||||
return staticSymbol ? staticSymbol.filePath : null;
|
return staticSymbol ? staticSymbol.filePath : null;
|
||||||
}
|
}
|
||||||
@ -129,14 +129,14 @@ export class StaticReflector implements ɵReflectorReader {
|
|||||||
const summary = this.summaryResolver.resolveSummary(parentType);
|
const summary = this.summaryResolver.resolveSummary(parentType);
|
||||||
if (summary && summary.type) {
|
if (summary && summary.type) {
|
||||||
const requiredAnnotationTypes =
|
const requiredAnnotationTypes =
|
||||||
this.annotationForParentClassWithSummaryKind.get(summary.type.summaryKind);
|
this.annotationForParentClassWithSummaryKind.get(summary.type.summaryKind !) !;
|
||||||
const typeHasRequiredAnnotation = requiredAnnotationTypes.some(
|
const typeHasRequiredAnnotation = requiredAnnotationTypes.some(
|
||||||
requiredType => ownAnnotations.some(ann => ann instanceof requiredType));
|
(requiredType: any) => ownAnnotations.some(ann => ann instanceof requiredType));
|
||||||
if (!typeHasRequiredAnnotation) {
|
if (!typeHasRequiredAnnotation) {
|
||||||
this.reportError(
|
this.reportError(
|
||||||
syntaxError(
|
syntaxError(
|
||||||
`Class ${type.name} in ${type.filePath} extends from a ${CompileSummaryKind[summary.type.summaryKind]} in another compilation unit without duplicating the decorator. ` +
|
`Class ${type.name} in ${type.filePath} extends from a ${CompileSummaryKind[summary.type.summaryKind!]} in another compilation unit without duplicating the decorator. ` +
|
||||||
`Please add a ${requiredAnnotationTypes.map(type => this.annotationNames.get(type)).join(' or ')} decorator to the class.`),
|
`Please add a ${requiredAnnotationTypes.map((type: any) => this.annotationNames.get(type)).join(' or ')} decorator to the class.`),
|
||||||
type);
|
type);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -155,7 +155,7 @@ export class StaticReflector implements ɵReflectorReader {
|
|||||||
if (parentType) {
|
if (parentType) {
|
||||||
const parentPropMetadata = this.propMetadata(parentType);
|
const parentPropMetadata = this.propMetadata(parentType);
|
||||||
Object.keys(parentPropMetadata).forEach((parentProp) => {
|
Object.keys(parentPropMetadata).forEach((parentProp) => {
|
||||||
propMetadata[parentProp] = parentPropMetadata[parentProp];
|
propMetadata ![parentProp] = parentPropMetadata[parentProp];
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -165,10 +165,10 @@ export class StaticReflector implements ɵReflectorReader {
|
|||||||
const prop = (<any[]>propData)
|
const prop = (<any[]>propData)
|
||||||
.find(a => a['__symbolic'] == 'property' || a['__symbolic'] == 'method');
|
.find(a => a['__symbolic'] == 'property' || a['__symbolic'] == 'method');
|
||||||
const decorators: any[] = [];
|
const decorators: any[] = [];
|
||||||
if (propMetadata[propName]) {
|
if (propMetadata ![propName]) {
|
||||||
decorators.push(...propMetadata[propName]);
|
decorators.push(...propMetadata ![propName]);
|
||||||
}
|
}
|
||||||
propMetadata[propName] = decorators;
|
propMetadata ![propName] = decorators;
|
||||||
if (prop && prop['decorators']) {
|
if (prop && prop['decorators']) {
|
||||||
decorators.push(...this.simplify(type, prop['decorators']));
|
decorators.push(...this.simplify(type, prop['decorators']));
|
||||||
}
|
}
|
||||||
@ -206,7 +206,7 @@ export class StaticReflector implements ɵReflectorReader {
|
|||||||
if (decorators) {
|
if (decorators) {
|
||||||
nestedResult.push(...decorators);
|
nestedResult.push(...decorators);
|
||||||
}
|
}
|
||||||
parameters.push(nestedResult);
|
parameters !.push(nestedResult);
|
||||||
});
|
});
|
||||||
} else if (parentType) {
|
} else if (parentType) {
|
||||||
parameters = this.parameters(parentType);
|
parameters = this.parameters(parentType);
|
||||||
@ -232,7 +232,7 @@ export class StaticReflector implements ɵReflectorReader {
|
|||||||
if (parentType) {
|
if (parentType) {
|
||||||
const parentMethodNames = this._methodNames(parentType);
|
const parentMethodNames = this._methodNames(parentType);
|
||||||
Object.keys(parentMethodNames).forEach((parentProp) => {
|
Object.keys(parentMethodNames).forEach((parentProp) => {
|
||||||
methodNames[parentProp] = parentMethodNames[parentProp];
|
methodNames ![parentProp] = parentMethodNames[parentProp];
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -240,14 +240,14 @@ export class StaticReflector implements ɵReflectorReader {
|
|||||||
Object.keys(members).forEach((propName) => {
|
Object.keys(members).forEach((propName) => {
|
||||||
const propData = members[propName];
|
const propData = members[propName];
|
||||||
const isMethod = (<any[]>propData).some(a => a['__symbolic'] == 'method');
|
const isMethod = (<any[]>propData).some(a => a['__symbolic'] == 'method');
|
||||||
methodNames[propName] = methodNames[propName] || isMethod;
|
methodNames ![propName] = methodNames ![propName] || isMethod;
|
||||||
});
|
});
|
||||||
this.methodCache.set(type, methodNames);
|
this.methodCache.set(type, methodNames);
|
||||||
}
|
}
|
||||||
return methodNames;
|
return methodNames;
|
||||||
}
|
}
|
||||||
|
|
||||||
private findParentType(type: StaticSymbol, classMetadata: any): StaticSymbol|null {
|
private findParentType(type: StaticSymbol, classMetadata: any): StaticSymbol|undefined {
|
||||||
const parentType = this.trySimplify(type, classMetadata['extends']);
|
const parentType = this.trySimplify(type, classMetadata['extends']);
|
||||||
if (parentType instanceof StaticSymbol) {
|
if (parentType instanceof StaticSymbol) {
|
||||||
return parentType;
|
return parentType;
|
||||||
|
@ -31,14 +31,14 @@ export interface StaticSymbolResolverHost {
|
|||||||
* @param modulePath is a string identifier for a module as an absolute path.
|
* @param modulePath is a string identifier for a module as an absolute path.
|
||||||
* @returns the metadata for the given module.
|
* @returns the metadata for the given module.
|
||||||
*/
|
*/
|
||||||
getMetadataFor(modulePath: string): {[key: string]: any}[];
|
getMetadataFor(modulePath: string): {[key: string]: any}[]|undefined;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Converts a module name that is used in an `import` to a file path.
|
* Converts a module name that is used in an `import` to a file path.
|
||||||
* I.e.
|
* I.e.
|
||||||
* `path/to/containingFile.ts` containing `import {...} from 'module-name'`.
|
* `path/to/containingFile.ts` containing `import {...} from 'module-name'`.
|
||||||
*/
|
*/
|
||||||
moduleNameToFileName(moduleName: string, containingFile: string): string /*|null*/;
|
moduleNameToFileName(moduleName: string, containingFile?: string): string|null;
|
||||||
}
|
}
|
||||||
|
|
||||||
const SUPPORTED_SCHEMA_VERSION = 3;
|
const SUPPORTED_SCHEMA_VERSION = 3;
|
||||||
@ -64,17 +64,17 @@ export class StaticSymbolResolver {
|
|||||||
constructor(
|
constructor(
|
||||||
private host: StaticSymbolResolverHost, private staticSymbolCache: StaticSymbolCache,
|
private host: StaticSymbolResolverHost, private staticSymbolCache: StaticSymbolCache,
|
||||||
private summaryResolver: SummaryResolver<StaticSymbol>,
|
private summaryResolver: SummaryResolver<StaticSymbol>,
|
||||||
private errorRecorder?: (error: any, fileName: string) => void) {}
|
private errorRecorder?: (error: any, fileName?: string) => void) {}
|
||||||
|
|
||||||
resolveSymbol(staticSymbol: StaticSymbol): ResolvedStaticSymbol {
|
resolveSymbol(staticSymbol: StaticSymbol): ResolvedStaticSymbol {
|
||||||
if (staticSymbol.members.length > 0) {
|
if (staticSymbol.members.length > 0) {
|
||||||
return this._resolveSymbolMembers(staticSymbol);
|
return this._resolveSymbolMembers(staticSymbol) !;
|
||||||
}
|
}
|
||||||
let result = this.resolvedSymbols.get(staticSymbol);
|
let result = this.resolvedSymbols.get(staticSymbol);
|
||||||
if (result) {
|
if (result) {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
result = this._resolveSymbolFromSummary(staticSymbol);
|
result = this._resolveSymbolFromSummary(staticSymbol) !;
|
||||||
if (result) {
|
if (result) {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@ -82,7 +82,7 @@ export class StaticSymbolResolver {
|
|||||||
// have summaries, only .d.ts files. So we always need to check both, the summary
|
// have summaries, only .d.ts files. So we always need to check both, the summary
|
||||||
// and metadata.
|
// and metadata.
|
||||||
this._createSymbolsOf(staticSymbol.filePath);
|
this._createSymbolsOf(staticSymbol.filePath);
|
||||||
result = this.resolvedSymbols.get(staticSymbol);
|
result = this.resolvedSymbols.get(staticSymbol) !;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -95,7 +95,7 @@ export class StaticSymbolResolver {
|
|||||||
*
|
*
|
||||||
* @param staticSymbol the symbol for which to generate a import symbol
|
* @param staticSymbol the symbol for which to generate a import symbol
|
||||||
*/
|
*/
|
||||||
getImportAs(staticSymbol: StaticSymbol): StaticSymbol {
|
getImportAs(staticSymbol: StaticSymbol): StaticSymbol|null {
|
||||||
if (staticSymbol.members.length) {
|
if (staticSymbol.members.length) {
|
||||||
const baseSymbol = this.getStaticSymbol(staticSymbol.filePath, staticSymbol.name);
|
const baseSymbol = this.getStaticSymbol(staticSymbol.filePath, staticSymbol.name);
|
||||||
const baseImportAs = this.getImportAs(baseSymbol);
|
const baseImportAs = this.getImportAs(baseSymbol);
|
||||||
@ -105,7 +105,7 @@ export class StaticSymbolResolver {
|
|||||||
}
|
}
|
||||||
let result = this.summaryResolver.getImportAs(staticSymbol);
|
let result = this.summaryResolver.getImportAs(staticSymbol);
|
||||||
if (!result) {
|
if (!result) {
|
||||||
result = this.importAs.get(staticSymbol);
|
result = this.importAs.get(staticSymbol) !;
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@ -123,7 +123,7 @@ export class StaticSymbolResolver {
|
|||||||
* getTypeArity returns the number of generic type parameters the given symbol
|
* getTypeArity returns the number of generic type parameters the given symbol
|
||||||
* has. If the symbol is not a type the result is null.
|
* has. If the symbol is not a type the result is null.
|
||||||
*/
|
*/
|
||||||
getTypeArity(staticSymbol: StaticSymbol): number /*|null*/ {
|
getTypeArity(staticSymbol: StaticSymbol): number|null {
|
||||||
// If the file is a factory file, don't resolve the symbol as doing so would
|
// If the file is a factory file, don't resolve the symbol as doing so would
|
||||||
// cause the metadata for an factory file to be loaded which doesn't exist.
|
// cause the metadata for an factory file to be loaded which doesn't exist.
|
||||||
// All references to generated classes must include the correct arity whenever
|
// All references to generated classes must include the correct arity whenever
|
||||||
@ -163,7 +163,7 @@ export class StaticSymbolResolver {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private _resolveSymbolMembers(staticSymbol: StaticSymbol): ResolvedStaticSymbol {
|
private _resolveSymbolMembers(staticSymbol: StaticSymbol): ResolvedStaticSymbol|null {
|
||||||
const members = staticSymbol.members;
|
const members = staticSymbol.members;
|
||||||
const baseResolvedSymbol =
|
const baseResolvedSymbol =
|
||||||
this.resolveSymbol(this.getStaticSymbol(staticSymbol.filePath, staticSymbol.name));
|
this.resolveSymbol(this.getStaticSymbol(staticSymbol.filePath, staticSymbol.name));
|
||||||
@ -188,7 +188,7 @@ export class StaticSymbolResolver {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
private _resolveSymbolFromSummary(staticSymbol: StaticSymbol): ResolvedStaticSymbol {
|
private _resolveSymbolFromSummary(staticSymbol: StaticSymbol): ResolvedStaticSymbol|null {
|
||||||
const summary = this.summaryResolver.resolveSummary(staticSymbol);
|
const summary = this.summaryResolver.resolveSummary(staticSymbol);
|
||||||
return summary ? new ResolvedStaticSymbol(staticSymbol, summary.metadata) : null;
|
return summary ? new ResolvedStaticSymbol(staticSymbol, summary.metadata) : null;
|
||||||
}
|
}
|
||||||
@ -252,7 +252,7 @@ export class StaticSymbolResolver {
|
|||||||
const originFilePath = this.resolveModule(origin, filePath);
|
const originFilePath = this.resolveModule(origin, filePath);
|
||||||
if (!originFilePath) {
|
if (!originFilePath) {
|
||||||
this.reportError(
|
this.reportError(
|
||||||
new Error(`Couldn't resolve original symbol for ${origin} from ${filePath}`), null);
|
new Error(`Couldn't resolve original symbol for ${origin} from ${filePath}`));
|
||||||
} else {
|
} else {
|
||||||
this.symbolResourcePaths.set(symbol, originFilePath);
|
this.symbolResourcePaths.set(symbol, originFilePath);
|
||||||
}
|
}
|
||||||
@ -337,7 +337,7 @@ export class StaticSymbolResolver {
|
|||||||
}
|
}
|
||||||
let filePath: string;
|
let filePath: string;
|
||||||
if (module) {
|
if (module) {
|
||||||
filePath = self.resolveModule(module, sourceSymbol.filePath);
|
filePath = self.resolveModule(module, sourceSymbol.filePath) !;
|
||||||
if (!filePath) {
|
if (!filePath) {
|
||||||
return {
|
return {
|
||||||
__symbolic: 'error',
|
__symbolic: 'error',
|
||||||
@ -381,7 +381,7 @@ export class StaticSymbolResolver {
|
|||||||
return new ResolvedStaticSymbol(sourceSymbol, targetSymbol);
|
return new ResolvedStaticSymbol(sourceSymbol, targetSymbol);
|
||||||
}
|
}
|
||||||
|
|
||||||
private reportError(error: Error, context: StaticSymbol, path?: string) {
|
private reportError(error: Error, context?: StaticSymbol, path?: string) {
|
||||||
if (this.errorRecorder) {
|
if (this.errorRecorder) {
|
||||||
this.errorRecorder(error, (context && context.filePath) || path);
|
this.errorRecorder(error, (context && context.filePath) || path);
|
||||||
} else {
|
} else {
|
||||||
@ -413,7 +413,7 @@ export class StaticSymbolResolver {
|
|||||||
const errorMessage = moduleMetadata['version'] == 2 ?
|
const errorMessage = moduleMetadata['version'] == 2 ?
|
||||||
`Unsupported metadata version ${moduleMetadata['version']} for module ${module}. This module should be compiled with a newer version of ngc` :
|
`Unsupported metadata version ${moduleMetadata['version']} for module ${module}. This module should be compiled with a newer version of ngc` :
|
||||||
`Metadata version mismatch for module ${module}, found version ${moduleMetadata['version']}, expected ${SUPPORTED_SCHEMA_VERSION}`;
|
`Metadata version mismatch for module ${module}, found version ${moduleMetadata['version']}, expected ${SUPPORTED_SCHEMA_VERSION}`;
|
||||||
this.reportError(new Error(errorMessage), null);
|
this.reportError(new Error(errorMessage));
|
||||||
}
|
}
|
||||||
this.metadataCache.set(module, moduleMetadata);
|
this.metadataCache.set(module, moduleMetadata);
|
||||||
}
|
}
|
||||||
@ -426,20 +426,20 @@ export class StaticSymbolResolver {
|
|||||||
this.reportError(
|
this.reportError(
|
||||||
new Error(`Could not resolve module ${module}${containingFile ? ` relative to $ {
|
new Error(`Could not resolve module ${module}${containingFile ? ` relative to $ {
|
||||||
containingFile
|
containingFile
|
||||||
} `: ''}`),
|
} `: ''}`));
|
||||||
null);
|
|
||||||
return this.getStaticSymbol(`ERROR:${module}`, symbolName);
|
return this.getStaticSymbol(`ERROR:${module}`, symbolName);
|
||||||
}
|
}
|
||||||
return this.getStaticSymbol(filePath, symbolName);
|
return this.getStaticSymbol(filePath, symbolName);
|
||||||
}
|
}
|
||||||
|
|
||||||
private resolveModule(module: string, containingFile: string): string {
|
private resolveModule(module: string, containingFile?: string): string|null {
|
||||||
try {
|
try {
|
||||||
return this.host.moduleNameToFileName(module, containingFile);
|
return this.host.moduleNameToFileName(module, containingFile);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
console.error(`Could not resolve module '${module}' relative to file ${containingFile}`);
|
console.error(`Could not resolve module '${module}' relative to file ${containingFile}`);
|
||||||
this.reportError(e, null, containingFile);
|
this.reportError(e, undefined, containingFile);
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -447,4 +447,4 @@ export class StaticSymbolResolver {
|
|||||||
// See https://github.com/Microsoft/TypeScript/blob/master/src/compiler/utilities.ts
|
// See https://github.com/Microsoft/TypeScript/blob/master/src/compiler/utilities.ts
|
||||||
export function unescapeIdentifier(identifier: string): string {
|
export function unescapeIdentifier(identifier: string): string {
|
||||||
return identifier.startsWith('___') ? identifier.substr(1) : identifier;
|
return identifier.startsWith('___') ? identifier.substr(1) : identifier;
|
||||||
}
|
}
|
||||||
|
@ -16,7 +16,7 @@ export interface AotSummaryResolverHost {
|
|||||||
/**
|
/**
|
||||||
* Loads an NgModule/Directive/Pipe summary file
|
* Loads an NgModule/Directive/Pipe summary file
|
||||||
*/
|
*/
|
||||||
loadSummary(filePath: string): string /*|null*/;
|
loadSummary(filePath: string): string|null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns whether a file is a source file or not.
|
* Returns whether a file is a source file or not.
|
||||||
@ -53,7 +53,7 @@ export class AotSummaryResolver implements SummaryResolver<StaticSymbol> {
|
|||||||
let summary = this.summaryCache.get(staticSymbol);
|
let summary = this.summaryCache.get(staticSymbol);
|
||||||
if (!summary) {
|
if (!summary) {
|
||||||
this._loadSummaryFile(staticSymbol.filePath);
|
this._loadSummaryFile(staticSymbol.filePath);
|
||||||
summary = this.summaryCache.get(staticSymbol);
|
summary = this.summaryCache.get(staticSymbol) !;
|
||||||
}
|
}
|
||||||
return summary;
|
return summary;
|
||||||
}
|
}
|
||||||
@ -65,7 +65,7 @@ export class AotSummaryResolver implements SummaryResolver<StaticSymbol> {
|
|||||||
|
|
||||||
getImportAs(staticSymbol: StaticSymbol): StaticSymbol {
|
getImportAs(staticSymbol: StaticSymbol): StaticSymbol {
|
||||||
staticSymbol.assertNoMembers();
|
staticSymbol.assertNoMembers();
|
||||||
return this.importAs.get(staticSymbol);
|
return this.importAs.get(staticSymbol) !;
|
||||||
}
|
}
|
||||||
|
|
||||||
private _loadSummaryFile(filePath: string) {
|
private _loadSummaryFile(filePath: string) {
|
||||||
@ -75,7 +75,7 @@ export class AotSummaryResolver implements SummaryResolver<StaticSymbol> {
|
|||||||
this.loadedFilePaths.add(filePath);
|
this.loadedFilePaths.add(filePath);
|
||||||
if (this.isLibraryFile(filePath)) {
|
if (this.isLibraryFile(filePath)) {
|
||||||
const summaryFilePath = summaryFileName(filePath);
|
const summaryFilePath = summaryFileName(filePath);
|
||||||
let json: string;
|
let json: string|null;
|
||||||
try {
|
try {
|
||||||
json = this.host.loadSummary(summaryFilePath);
|
json = this.host.loadSummary(summaryFilePath);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
|
@ -133,7 +133,7 @@ class Serializer extends ValueTransformer {
|
|||||||
summaries: this.processedSummaries,
|
summaries: this.processedSummaries,
|
||||||
symbols: this.symbols.map((symbol, index) => {
|
symbols: this.symbols.map((symbol, index) => {
|
||||||
symbol.assertNoMembers();
|
symbol.assertNoMembers();
|
||||||
let importAs: string;
|
let importAs: string = undefined !;
|
||||||
if (this.summaryResolver.isLibraryFile(symbol.filePath)) {
|
if (this.summaryResolver.isLibraryFile(symbol.filePath)) {
|
||||||
importAs = `${symbol.name}_${index}`;
|
importAs = `${symbol.name}_${index}`;
|
||||||
exportAs.push({symbol, exportAs: importAs});
|
exportAs.push({symbol, exportAs: importAs});
|
||||||
|
@ -22,7 +22,8 @@ const HOST_REG_EXP = /^(?:(?:\[([^\]]+)\])|(?:\(([^\)]+)\)))|(\@[-\w]+)$/;
|
|||||||
|
|
||||||
export class CompileAnimationEntryMetadata {
|
export class CompileAnimationEntryMetadata {
|
||||||
constructor(
|
constructor(
|
||||||
public name: string = null, public definitions: CompileAnimationStateMetadata[] = null) {}
|
public name: string|null = null,
|
||||||
|
public definitions: CompileAnimationStateMetadata[]|null = null) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
export abstract class CompileAnimationStateMetadata {}
|
export abstract class CompileAnimationStateMetadata {}
|
||||||
@ -49,7 +50,8 @@ export class CompileAnimationKeyframesSequenceMetadata extends CompileAnimationM
|
|||||||
|
|
||||||
export class CompileAnimationStyleMetadata extends CompileAnimationMetadata {
|
export class CompileAnimationStyleMetadata extends CompileAnimationMetadata {
|
||||||
constructor(
|
constructor(
|
||||||
public offset: number, public styles: Array<string|{[key: string]: string | number}> = null) {
|
public offset: number,
|
||||||
|
public styles: Array<string|{[key: string]: string | number}>|null = null) {
|
||||||
super();
|
super();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -57,21 +59,21 @@ export class CompileAnimationStyleMetadata extends CompileAnimationMetadata {
|
|||||||
export class CompileAnimationAnimateMetadata extends CompileAnimationMetadata {
|
export class CompileAnimationAnimateMetadata extends CompileAnimationMetadata {
|
||||||
constructor(
|
constructor(
|
||||||
public timings: string|number = 0, public styles: CompileAnimationStyleMetadata|
|
public timings: string|number = 0, public styles: CompileAnimationStyleMetadata|
|
||||||
CompileAnimationKeyframesSequenceMetadata = null) {
|
CompileAnimationKeyframesSequenceMetadata|null = null) {
|
||||||
super();
|
super();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export abstract class CompileAnimationWithStepsMetadata extends CompileAnimationMetadata {
|
export abstract class CompileAnimationWithStepsMetadata extends CompileAnimationMetadata {
|
||||||
constructor(public steps: CompileAnimationMetadata[] = null) { super(); }
|
constructor(public steps: CompileAnimationMetadata[]|null = null) { super(); }
|
||||||
}
|
}
|
||||||
|
|
||||||
export class CompileAnimationSequenceMetadata extends CompileAnimationWithStepsMetadata {
|
export class CompileAnimationSequenceMetadata extends CompileAnimationWithStepsMetadata {
|
||||||
constructor(steps: CompileAnimationMetadata[] = null) { super(steps); }
|
constructor(steps: CompileAnimationMetadata[]|null = null) { super(steps); }
|
||||||
}
|
}
|
||||||
|
|
||||||
export class CompileAnimationGroupMetadata extends CompileAnimationWithStepsMetadata {
|
export class CompileAnimationGroupMetadata extends CompileAnimationWithStepsMetadata {
|
||||||
constructor(steps: CompileAnimationMetadata[] = null) { super(steps); }
|
constructor(steps: CompileAnimationMetadata[]|null = null) { super(steps); }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -81,7 +83,8 @@ function _sanitizeIdentifier(name: string): string {
|
|||||||
|
|
||||||
let _anonymousTypeIndex = 0;
|
let _anonymousTypeIndex = 0;
|
||||||
|
|
||||||
export function identifierName(compileIdentifier: CompileIdentifierMetadata): string {
|
export function identifierName(compileIdentifier: CompileIdentifierMetadata | null | undefined):
|
||||||
|
string|null {
|
||||||
if (!compileIdentifier || !compileIdentifier.reference) {
|
if (!compileIdentifier || !compileIdentifier.reference) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
@ -148,7 +151,7 @@ export enum CompileSummaryKind {
|
|||||||
* the directive / module itself.
|
* the directive / module itself.
|
||||||
*/
|
*/
|
||||||
export interface CompileTypeSummary {
|
export interface CompileTypeSummary {
|
||||||
summaryKind: CompileSummaryKind;
|
summaryKind: CompileSummaryKind|null;
|
||||||
type: CompileTypeMetadata;
|
type: CompileTypeMetadata;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -216,13 +219,13 @@ export interface CompileQueryMetadata {
|
|||||||
* Metadata about a stylesheet
|
* Metadata about a stylesheet
|
||||||
*/
|
*/
|
||||||
export class CompileStylesheetMetadata {
|
export class CompileStylesheetMetadata {
|
||||||
moduleUrl: string;
|
moduleUrl: string|null;
|
||||||
styles: string[];
|
styles: string[];
|
||||||
styleUrls: string[];
|
styleUrls: string[];
|
||||||
constructor(
|
constructor(
|
||||||
{moduleUrl, styles,
|
{moduleUrl, styles,
|
||||||
styleUrls}: {moduleUrl?: string, styles?: string[], styleUrls?: string[]} = {}) {
|
styleUrls}: {moduleUrl?: string, styles?: string[], styleUrls?: string[]} = {}) {
|
||||||
this.moduleUrl = moduleUrl;
|
this.moduleUrl = moduleUrl || null;
|
||||||
this.styles = _normalizeArray(styles);
|
this.styles = _normalizeArray(styles);
|
||||||
this.styleUrls = _normalizeArray(styleUrls);
|
this.styleUrls = _normalizeArray(styleUrls);
|
||||||
}
|
}
|
||||||
@ -232,39 +235,38 @@ export class CompileStylesheetMetadata {
|
|||||||
* Summary Metadata regarding compilation of a template.
|
* Summary Metadata regarding compilation of a template.
|
||||||
*/
|
*/
|
||||||
export interface CompileTemplateSummary {
|
export interface CompileTemplateSummary {
|
||||||
animations: string[];
|
animations: string[]|null;
|
||||||
ngContentSelectors: string[];
|
ngContentSelectors: string[];
|
||||||
encapsulation: ViewEncapsulation;
|
encapsulation: ViewEncapsulation|null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Metadata regarding compilation of a template.
|
* Metadata regarding compilation of a template.
|
||||||
*/
|
*/
|
||||||
export class CompileTemplateMetadata {
|
export class CompileTemplateMetadata {
|
||||||
encapsulation: ViewEncapsulation;
|
encapsulation: ViewEncapsulation|null;
|
||||||
template: string;
|
template: string|null;
|
||||||
templateUrl: string;
|
templateUrl: string|null;
|
||||||
isInline: boolean;
|
isInline: boolean;
|
||||||
styles: string[];
|
styles: string[];
|
||||||
styleUrls: string[];
|
styleUrls: string[];
|
||||||
externalStylesheets: CompileStylesheetMetadata[];
|
externalStylesheets: CompileStylesheetMetadata[];
|
||||||
animations: any[];
|
animations: any[];
|
||||||
ngContentSelectors: string[];
|
ngContentSelectors: string[];
|
||||||
interpolation: [string, string];
|
interpolation: [string, string]|null;
|
||||||
constructor(
|
constructor({encapsulation, template, templateUrl, styles, styleUrls, externalStylesheets,
|
||||||
{encapsulation, template, templateUrl, styles, styleUrls, externalStylesheets, animations,
|
animations, ngContentSelectors, interpolation, isInline}: {
|
||||||
ngContentSelectors, interpolation, isInline}: {
|
encapsulation: ViewEncapsulation | null,
|
||||||
encapsulation?: ViewEncapsulation,
|
template: string|null,
|
||||||
template?: string,
|
templateUrl: string|null,
|
||||||
templateUrl?: string,
|
styles: string[],
|
||||||
styles?: string[],
|
styleUrls: string[],
|
||||||
styleUrls?: string[],
|
externalStylesheets: CompileStylesheetMetadata[],
|
||||||
externalStylesheets?: CompileStylesheetMetadata[],
|
ngContentSelectors: string[],
|
||||||
ngContentSelectors?: string[],
|
animations: any[],
|
||||||
animations?: any[],
|
interpolation: [string, string]|null,
|
||||||
interpolation?: [string, string],
|
isInline: boolean
|
||||||
isInline?: boolean
|
}) {
|
||||||
} = {}) {
|
|
||||||
this.encapsulation = encapsulation;
|
this.encapsulation = encapsulation;
|
||||||
this.template = template;
|
this.template = template;
|
||||||
this.templateUrl = templateUrl;
|
this.templateUrl = templateUrl;
|
||||||
@ -299,8 +301,8 @@ export interface CompileEntryComponentMetadata {
|
|||||||
export interface CompileDirectiveSummary extends CompileTypeSummary {
|
export interface CompileDirectiveSummary extends CompileTypeSummary {
|
||||||
type: CompileTypeMetadata;
|
type: CompileTypeMetadata;
|
||||||
isComponent: boolean;
|
isComponent: boolean;
|
||||||
selector: string;
|
selector: string|null;
|
||||||
exportAs: string;
|
exportAs: string|null;
|
||||||
inputs: {[key: string]: string};
|
inputs: {[key: string]: string};
|
||||||
outputs: {[key: string]: string};
|
outputs: {[key: string]: string};
|
||||||
hostListeners: {[key: string]: string};
|
hostListeners: {[key: string]: string};
|
||||||
@ -311,40 +313,39 @@ export interface CompileDirectiveSummary extends CompileTypeSummary {
|
|||||||
queries: CompileQueryMetadata[];
|
queries: CompileQueryMetadata[];
|
||||||
viewQueries: CompileQueryMetadata[];
|
viewQueries: CompileQueryMetadata[];
|
||||||
entryComponents: CompileEntryComponentMetadata[];
|
entryComponents: CompileEntryComponentMetadata[];
|
||||||
changeDetection: ChangeDetectionStrategy;
|
changeDetection: ChangeDetectionStrategy|null;
|
||||||
template: CompileTemplateSummary;
|
template: CompileTemplateSummary|null;
|
||||||
componentViewType: StaticSymbol|ProxyClass;
|
componentViewType: StaticSymbol|ProxyClass|null;
|
||||||
rendererType: StaticSymbol|RendererType2;
|
rendererType: StaticSymbol|RendererType2|null;
|
||||||
componentFactory: StaticSymbol|ComponentFactory<any>;
|
componentFactory: StaticSymbol|ComponentFactory<any>|null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Metadata regarding compilation of a directive.
|
* Metadata regarding compilation of a directive.
|
||||||
*/
|
*/
|
||||||
export class CompileDirectiveMetadata {
|
export class CompileDirectiveMetadata {
|
||||||
static create(
|
static create({isHost, type, isComponent, selector, exportAs, changeDetection, inputs, outputs,
|
||||||
{isHost, type, isComponent, selector, exportAs, changeDetection, inputs, outputs, host,
|
host, providers, viewProviders, queries, viewQueries, entryComponents, template,
|
||||||
providers, viewProviders, queries, viewQueries, entryComponents, template, componentViewType,
|
componentViewType, rendererType, componentFactory}: {
|
||||||
rendererType, componentFactory}: {
|
isHost: boolean,
|
||||||
isHost?: boolean,
|
type: CompileTypeMetadata,
|
||||||
type?: CompileTypeMetadata,
|
isComponent: boolean,
|
||||||
isComponent?: boolean,
|
selector: string|null,
|
||||||
selector?: string,
|
exportAs: string|null,
|
||||||
exportAs?: string,
|
changeDetection: ChangeDetectionStrategy|null,
|
||||||
changeDetection?: ChangeDetectionStrategy,
|
inputs: string[],
|
||||||
inputs?: string[],
|
outputs: string[],
|
||||||
outputs?: string[],
|
host: {[key: string]: string},
|
||||||
host?: {[key: string]: string},
|
providers: CompileProviderMetadata[],
|
||||||
providers?: CompileProviderMetadata[],
|
viewProviders: CompileProviderMetadata[],
|
||||||
viewProviders?: CompileProviderMetadata[],
|
queries: CompileQueryMetadata[],
|
||||||
queries?: CompileQueryMetadata[],
|
viewQueries: CompileQueryMetadata[],
|
||||||
viewQueries?: CompileQueryMetadata[],
|
entryComponents: CompileEntryComponentMetadata[],
|
||||||
entryComponents?: CompileEntryComponentMetadata[],
|
template: CompileTemplateMetadata,
|
||||||
template?: CompileTemplateMetadata,
|
componentViewType: StaticSymbol|ProxyClass|null,
|
||||||
componentViewType?: StaticSymbol|ProxyClass,
|
rendererType: StaticSymbol|RendererType2|null,
|
||||||
rendererType?: StaticSymbol|RendererType2,
|
componentFactory: StaticSymbol|ComponentFactory<any>|null,
|
||||||
componentFactory?: StaticSymbol|ComponentFactory<any>,
|
}): CompileDirectiveMetadata {
|
||||||
} = {}): CompileDirectiveMetadata {
|
|
||||||
const hostListeners: {[key: string]: string} = {};
|
const hostListeners: {[key: string]: string} = {};
|
||||||
const hostProperties: {[key: string]: string} = {};
|
const hostProperties: {[key: string]: string} = {};
|
||||||
const hostAttributes: {[key: string]: string} = {};
|
const hostAttributes: {[key: string]: string} = {};
|
||||||
@ -403,9 +404,9 @@ export class CompileDirectiveMetadata {
|
|||||||
isHost: boolean;
|
isHost: boolean;
|
||||||
type: CompileTypeMetadata;
|
type: CompileTypeMetadata;
|
||||||
isComponent: boolean;
|
isComponent: boolean;
|
||||||
selector: string;
|
selector: string|null;
|
||||||
exportAs: string;
|
exportAs: string|null;
|
||||||
changeDetection: ChangeDetectionStrategy;
|
changeDetection: ChangeDetectionStrategy|null;
|
||||||
inputs: {[key: string]: string};
|
inputs: {[key: string]: string};
|
||||||
outputs: {[key: string]: string};
|
outputs: {[key: string]: string};
|
||||||
hostListeners: {[key: string]: string};
|
hostListeners: {[key: string]: string};
|
||||||
@ -417,37 +418,37 @@ export class CompileDirectiveMetadata {
|
|||||||
viewQueries: CompileQueryMetadata[];
|
viewQueries: CompileQueryMetadata[];
|
||||||
entryComponents: CompileEntryComponentMetadata[];
|
entryComponents: CompileEntryComponentMetadata[];
|
||||||
|
|
||||||
template: CompileTemplateMetadata;
|
template: CompileTemplateMetadata|null;
|
||||||
|
|
||||||
componentViewType: StaticSymbol|ProxyClass;
|
componentViewType: StaticSymbol|ProxyClass|null;
|
||||||
rendererType: StaticSymbol|RendererType2;
|
rendererType: StaticSymbol|RendererType2|null;
|
||||||
componentFactory: StaticSymbol|ComponentFactory<any>;
|
componentFactory: StaticSymbol|ComponentFactory<any>|null;
|
||||||
|
|
||||||
constructor({isHost, type, isComponent, selector, exportAs,
|
constructor({isHost, type, isComponent, selector, exportAs,
|
||||||
changeDetection, inputs, outputs, hostListeners, hostProperties,
|
changeDetection, inputs, outputs, hostListeners, hostProperties,
|
||||||
hostAttributes, providers, viewProviders, queries, viewQueries,
|
hostAttributes, providers, viewProviders, queries, viewQueries,
|
||||||
entryComponents, template, componentViewType, rendererType, componentFactory}: {
|
entryComponents, template, componentViewType, rendererType, componentFactory}: {
|
||||||
isHost?: boolean,
|
isHost: boolean,
|
||||||
type?: CompileTypeMetadata,
|
type: CompileTypeMetadata,
|
||||||
isComponent?: boolean,
|
isComponent: boolean,
|
||||||
selector?: string,
|
selector: string|null,
|
||||||
exportAs?: string,
|
exportAs: string|null,
|
||||||
changeDetection?: ChangeDetectionStrategy,
|
changeDetection: ChangeDetectionStrategy|null,
|
||||||
inputs?: {[key: string]: string},
|
inputs: {[key: string]: string},
|
||||||
outputs?: {[key: string]: string},
|
outputs: {[key: string]: string},
|
||||||
hostListeners?: {[key: string]: string},
|
hostListeners: {[key: string]: string},
|
||||||
hostProperties?: {[key: string]: string},
|
hostProperties: {[key: string]: string},
|
||||||
hostAttributes?: {[key: string]: string},
|
hostAttributes: {[key: string]: string},
|
||||||
providers?: CompileProviderMetadata[],
|
providers: CompileProviderMetadata[],
|
||||||
viewProviders?: CompileProviderMetadata[],
|
viewProviders: CompileProviderMetadata[],
|
||||||
queries?: CompileQueryMetadata[],
|
queries: CompileQueryMetadata[],
|
||||||
viewQueries?: CompileQueryMetadata[],
|
viewQueries: CompileQueryMetadata[],
|
||||||
entryComponents?: CompileEntryComponentMetadata[],
|
entryComponents: CompileEntryComponentMetadata[],
|
||||||
template?: CompileTemplateMetadata,
|
template: CompileTemplateMetadata|null,
|
||||||
componentViewType?: StaticSymbol|ProxyClass,
|
componentViewType: StaticSymbol|ProxyClass|null,
|
||||||
rendererType?: StaticSymbol|RendererType2,
|
rendererType: StaticSymbol|RendererType2|null,
|
||||||
componentFactory?: StaticSymbol|ComponentFactory<any>,
|
componentFactory: StaticSymbol|ComponentFactory<any>|null,
|
||||||
} = {}) {
|
}) {
|
||||||
this.isHost = !!isHost;
|
this.isHost = !!isHost;
|
||||||
this.type = type;
|
this.type = type;
|
||||||
this.isComponent = isComponent;
|
this.isComponent = isComponent;
|
||||||
@ -503,7 +504,7 @@ export class CompileDirectiveMetadata {
|
|||||||
export function createHostComponentMeta(
|
export function createHostComponentMeta(
|
||||||
hostTypeReference: any, compMeta: CompileDirectiveMetadata,
|
hostTypeReference: any, compMeta: CompileDirectiveMetadata,
|
||||||
hostViewType: StaticSymbol | ProxyClass): CompileDirectiveMetadata {
|
hostViewType: StaticSymbol | ProxyClass): CompileDirectiveMetadata {
|
||||||
const template = CssSelector.parse(compMeta.selector)[0].getMatchingElementTemplate();
|
const template = CssSelector.parse(compMeta.selector !)[0].getMatchingElementTemplate();
|
||||||
return CompileDirectiveMetadata.create({
|
return CompileDirectiveMetadata.create({
|
||||||
isHost: true,
|
isHost: true,
|
||||||
type: {reference: hostTypeReference, diDeps: [], lifecycleHooks: []},
|
type: {reference: hostTypeReference, diDeps: [], lifecycleHooks: []},
|
||||||
@ -516,7 +517,10 @@ export function createHostComponentMeta(
|
|||||||
ngContentSelectors: [],
|
ngContentSelectors: [],
|
||||||
animations: [],
|
animations: [],
|
||||||
isInline: true,
|
isInline: true,
|
||||||
|
externalStylesheets: [],
|
||||||
|
interpolation: null
|
||||||
}),
|
}),
|
||||||
|
exportAs: null,
|
||||||
changeDetection: ChangeDetectionStrategy.Default,
|
changeDetection: ChangeDetectionStrategy.Default,
|
||||||
inputs: [],
|
inputs: [],
|
||||||
outputs: [],
|
outputs: [],
|
||||||
@ -528,7 +532,9 @@ export function createHostComponentMeta(
|
|||||||
queries: [],
|
queries: [],
|
||||||
viewQueries: [],
|
viewQueries: [],
|
||||||
componentViewType: hostViewType,
|
componentViewType: hostViewType,
|
||||||
rendererType: {id: '__Host__', encapsulation: ViewEncapsulation.None, styles: [], data: {}}
|
rendererType: {id: '__Host__', encapsulation: ViewEncapsulation.None, styles: [], data: {}},
|
||||||
|
entryComponents: [],
|
||||||
|
componentFactory: null
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -544,10 +550,10 @@ export class CompilePipeMetadata {
|
|||||||
pure: boolean;
|
pure: boolean;
|
||||||
|
|
||||||
constructor({type, name, pure}: {
|
constructor({type, name, pure}: {
|
||||||
type?: CompileTypeMetadata,
|
type: CompileTypeMetadata,
|
||||||
name?: string,
|
name: string,
|
||||||
pure?: boolean,
|
pure: boolean,
|
||||||
} = {}) {
|
}) {
|
||||||
this.type = type;
|
this.type = type;
|
||||||
this.name = name;
|
this.name = name;
|
||||||
this.pure = !!pure;
|
this.pure = !!pure;
|
||||||
@ -598,29 +604,28 @@ export class CompileNgModuleMetadata {
|
|||||||
importedModules: CompileNgModuleSummary[];
|
importedModules: CompileNgModuleSummary[];
|
||||||
exportedModules: CompileNgModuleSummary[];
|
exportedModules: CompileNgModuleSummary[];
|
||||||
schemas: SchemaMetadata[];
|
schemas: SchemaMetadata[];
|
||||||
id: string;
|
id: string|null;
|
||||||
|
|
||||||
transitiveModule: TransitiveCompileNgModuleMetadata;
|
transitiveModule: TransitiveCompileNgModuleMetadata;
|
||||||
|
|
||||||
constructor(
|
constructor({type, providers, declaredDirectives, exportedDirectives, declaredPipes,
|
||||||
{type, providers, declaredDirectives, exportedDirectives, declaredPipes, exportedPipes,
|
exportedPipes, entryComponents, bootstrapComponents, importedModules,
|
||||||
entryComponents, bootstrapComponents, importedModules, exportedModules, schemas,
|
exportedModules, schemas, transitiveModule, id}: {
|
||||||
transitiveModule, id}: {
|
type: CompileTypeMetadata,
|
||||||
type?: CompileTypeMetadata,
|
providers: CompileProviderMetadata[],
|
||||||
providers?: CompileProviderMetadata[],
|
declaredDirectives: CompileIdentifierMetadata[],
|
||||||
declaredDirectives?: CompileIdentifierMetadata[],
|
exportedDirectives: CompileIdentifierMetadata[],
|
||||||
exportedDirectives?: CompileIdentifierMetadata[],
|
declaredPipes: CompileIdentifierMetadata[],
|
||||||
declaredPipes?: CompileIdentifierMetadata[],
|
exportedPipes: CompileIdentifierMetadata[],
|
||||||
exportedPipes?: CompileIdentifierMetadata[],
|
entryComponents: CompileEntryComponentMetadata[],
|
||||||
entryComponents?: CompileEntryComponentMetadata[],
|
bootstrapComponents: CompileIdentifierMetadata[],
|
||||||
bootstrapComponents?: CompileIdentifierMetadata[],
|
importedModules: CompileNgModuleSummary[],
|
||||||
importedModules?: CompileNgModuleSummary[],
|
exportedModules: CompileNgModuleSummary[],
|
||||||
exportedModules?: CompileNgModuleSummary[],
|
transitiveModule: TransitiveCompileNgModuleMetadata,
|
||||||
transitiveModule?: TransitiveCompileNgModuleMetadata,
|
schemas: SchemaMetadata[],
|
||||||
schemas?: SchemaMetadata[],
|
id: string|null
|
||||||
id?: string
|
}) {
|
||||||
} = {}) {
|
this.type = type || null;
|
||||||
this.type = type;
|
|
||||||
this.declaredDirectives = _normalizeArray(declaredDirectives);
|
this.declaredDirectives = _normalizeArray(declaredDirectives);
|
||||||
this.exportedDirectives = _normalizeArray(exportedDirectives);
|
this.exportedDirectives = _normalizeArray(exportedDirectives);
|
||||||
this.declaredPipes = _normalizeArray(declaredPipes);
|
this.declaredPipes = _normalizeArray(declaredPipes);
|
||||||
@ -631,19 +636,20 @@ export class CompileNgModuleMetadata {
|
|||||||
this.importedModules = _normalizeArray(importedModules);
|
this.importedModules = _normalizeArray(importedModules);
|
||||||
this.exportedModules = _normalizeArray(exportedModules);
|
this.exportedModules = _normalizeArray(exportedModules);
|
||||||
this.schemas = _normalizeArray(schemas);
|
this.schemas = _normalizeArray(schemas);
|
||||||
this.id = id;
|
this.id = id || null;
|
||||||
this.transitiveModule = transitiveModule;
|
this.transitiveModule = transitiveModule || null;
|
||||||
}
|
}
|
||||||
|
|
||||||
toSummary(): CompileNgModuleSummary {
|
toSummary(): CompileNgModuleSummary {
|
||||||
|
const module = this.transitiveModule !;
|
||||||
return {
|
return {
|
||||||
summaryKind: CompileSummaryKind.NgModule,
|
summaryKind: CompileSummaryKind.NgModule,
|
||||||
type: this.type,
|
type: this.type,
|
||||||
entryComponents: this.transitiveModule.entryComponents,
|
entryComponents: module.entryComponents,
|
||||||
providers: this.transitiveModule.providers,
|
providers: module.providers,
|
||||||
modules: this.transitiveModule.modules,
|
modules: module.modules,
|
||||||
exportedDirectives: this.transitiveModule.exportedDirectives,
|
exportedDirectives: module.exportedDirectives,
|
||||||
exportedPipes: this.transitiveModule.exportedPipes
|
exportedPipes: module.exportedPipes
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -706,33 +712,33 @@ export class TransitiveCompileNgModuleMetadata {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function _normalizeArray(obj: any[]): any[] {
|
function _normalizeArray(obj: any[] | undefined | null): any[] {
|
||||||
return obj || [];
|
return obj || [];
|
||||||
}
|
}
|
||||||
|
|
||||||
export class ProviderMeta {
|
export class ProviderMeta {
|
||||||
token: any;
|
token: any;
|
||||||
useClass: Type<any>;
|
useClass: Type<any>|null;
|
||||||
useValue: any;
|
useValue: any;
|
||||||
useExisting: any;
|
useExisting: any;
|
||||||
useFactory: Function;
|
useFactory: Function|null;
|
||||||
dependencies: Object[];
|
dependencies: Object[]|null;
|
||||||
multi: boolean;
|
multi: boolean;
|
||||||
|
|
||||||
constructor(token: any, {useClass, useValue, useExisting, useFactory, deps, multi}: {
|
constructor(token: any, {useClass, useValue, useExisting, useFactory, deps, multi}: {
|
||||||
useClass?: Type<any>,
|
useClass?: Type<any>,
|
||||||
useValue?: any,
|
useValue?: any,
|
||||||
useExisting?: any,
|
useExisting?: any,
|
||||||
useFactory?: Function,
|
useFactory?: Function|null,
|
||||||
deps?: Object[],
|
deps?: Object[]|null,
|
||||||
multi?: boolean
|
multi?: boolean
|
||||||
}) {
|
}) {
|
||||||
this.token = token;
|
this.token = token;
|
||||||
this.useClass = useClass;
|
this.useClass = useClass || null;
|
||||||
this.useValue = useValue;
|
this.useValue = useValue;
|
||||||
this.useExisting = useExisting;
|
this.useExisting = useExisting;
|
||||||
this.useFactory = useFactory;
|
this.useFactory = useFactory || null;
|
||||||
this.dependencies = deps;
|
this.dependencies = deps || null;
|
||||||
this.multi = !!multi;
|
this.multi = !!multi;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -752,7 +758,7 @@ export function sourceUrl(url: string) {
|
|||||||
|
|
||||||
export function templateSourceUrl(
|
export function templateSourceUrl(
|
||||||
ngModuleType: CompileIdentifierMetadata, compMeta: {type: CompileIdentifierMetadata},
|
ngModuleType: CompileIdentifierMetadata, compMeta: {type: CompileIdentifierMetadata},
|
||||||
templateMeta: {isInline: boolean, templateUrl: string}) {
|
templateMeta: {isInline: boolean, templateUrl: string | null}) {
|
||||||
let url: string;
|
let url: string;
|
||||||
if (templateMeta.isInline) {
|
if (templateMeta.isInline) {
|
||||||
if (compMeta.type.reference instanceof StaticSymbol) {
|
if (compMeta.type.reference instanceof StaticSymbol) {
|
||||||
@ -763,7 +769,7 @@ export function templateSourceUrl(
|
|||||||
url = `${identifierName(ngModuleType)}/${identifierName(compMeta.type)}.html`;
|
url = `${identifierName(ngModuleType)}/${identifierName(compMeta.type)}.html`;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
url = templateMeta.templateUrl;
|
url = templateMeta.templateUrl !;
|
||||||
}
|
}
|
||||||
// always prepend ng:// to make angular resources easy to find and not clobber
|
// always prepend ng:// to make angular resources easy to find and not clobber
|
||||||
// user resources.
|
// user resources.
|
||||||
@ -771,7 +777,7 @@ export function templateSourceUrl(
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function sharedStylesheetJitUrl(meta: CompileStylesheetMetadata, id: number) {
|
export function sharedStylesheetJitUrl(meta: CompileStylesheetMetadata, id: number) {
|
||||||
const pathParts = meta.moduleUrl.split(/\/\\/g);
|
const pathParts = meta.moduleUrl !.split(/\/\\/g);
|
||||||
const baseName = pathParts[pathParts.length - 1];
|
const baseName = pathParts[pathParts.length - 1];
|
||||||
return sourceUrl(`css/${id}${baseName}.ngstyle.js`);
|
return sourceUrl(`css/${id}${baseName}.ngstyle.js`);
|
||||||
}
|
}
|
||||||
|
@ -13,7 +13,7 @@ import * as o from '../output/output_ast';
|
|||||||
|
|
||||||
export class EventHandlerVars { static event = o.variable('$event'); }
|
export class EventHandlerVars { static event = o.variable('$event'); }
|
||||||
|
|
||||||
export interface LocalResolver { getLocal(name: string): o.Expression; }
|
export interface LocalResolver { getLocal(name: string): o.Expression|null; }
|
||||||
|
|
||||||
export class ConvertActionBindingResult {
|
export class ConvertActionBindingResult {
|
||||||
constructor(public stmts: o.Statement[], public allowDefault: o.ReadVarExpr) {}
|
constructor(public stmts: o.Statement[], public allowDefault: o.ReadVarExpr) {}
|
||||||
@ -24,7 +24,7 @@ export class ConvertActionBindingResult {
|
|||||||
* used in an action binding (e.g. an event handler).
|
* used in an action binding (e.g. an event handler).
|
||||||
*/
|
*/
|
||||||
export function convertActionBinding(
|
export function convertActionBinding(
|
||||||
localResolver: LocalResolver, implicitReceiver: o.Expression, action: cdAst.AST,
|
localResolver: LocalResolver | null, implicitReceiver: o.Expression, action: cdAst.AST,
|
||||||
bindingId: string): ConvertActionBindingResult {
|
bindingId: string): ConvertActionBindingResult {
|
||||||
if (!localResolver) {
|
if (!localResolver) {
|
||||||
localResolver = new DefaultLocalResolver();
|
localResolver = new DefaultLocalResolver();
|
||||||
@ -51,7 +51,7 @@ export function convertActionBinding(
|
|||||||
flattenStatements(actionWithoutBuiltins.visit(visitor, _Mode.Statement), actionStmts);
|
flattenStatements(actionWithoutBuiltins.visit(visitor, _Mode.Statement), actionStmts);
|
||||||
prependTemporaryDecls(visitor.temporaryCount, bindingId, actionStmts);
|
prependTemporaryDecls(visitor.temporaryCount, bindingId, actionStmts);
|
||||||
const lastIndex = actionStmts.length - 1;
|
const lastIndex = actionStmts.length - 1;
|
||||||
let preventDefaultVar: o.ReadVarExpr = null;
|
let preventDefaultVar: o.ReadVarExpr = null !;
|
||||||
if (lastIndex >= 0) {
|
if (lastIndex >= 0) {
|
||||||
const lastStatement = actionStmts[lastIndex];
|
const lastStatement = actionStmts[lastIndex];
|
||||||
const returnExpr = convertStmtIntoExpression(lastStatement);
|
const returnExpr = convertStmtIntoExpression(lastStatement);
|
||||||
@ -90,7 +90,7 @@ export class ConvertPropertyBindingResult {
|
|||||||
* `convertPropertyBindingBuiltins`.
|
* `convertPropertyBindingBuiltins`.
|
||||||
*/
|
*/
|
||||||
export function convertPropertyBinding(
|
export function convertPropertyBinding(
|
||||||
localResolver: LocalResolver, implicitReceiver: o.Expression,
|
localResolver: LocalResolver | null, implicitReceiver: o.Expression,
|
||||||
expressionWithoutBuiltins: cdAst.AST, bindingId: string): ConvertPropertyBindingResult {
|
expressionWithoutBuiltins: cdAst.AST, bindingId: string): ConvertPropertyBindingResult {
|
||||||
if (!localResolver) {
|
if (!localResolver) {
|
||||||
localResolver = new DefaultLocalResolver();
|
localResolver = new DefaultLocalResolver();
|
||||||
@ -266,7 +266,7 @@ class _AstToIrVisitor implements cdAst.AstVisitor {
|
|||||||
if (ast instanceof BuiltinFunctionCall) {
|
if (ast instanceof BuiltinFunctionCall) {
|
||||||
fnResult = ast.converter(convertedArgs);
|
fnResult = ast.converter(convertedArgs);
|
||||||
} else {
|
} else {
|
||||||
fnResult = this.visit(ast.target, _Mode.Expression).callFn(convertedArgs);
|
fnResult = this.visit(ast.target !, _Mode.Expression).callFn(convertedArgs);
|
||||||
}
|
}
|
||||||
return convertToStatementIfNeeded(mode, fnResult);
|
return convertToStatementIfNeeded(mode, fnResult);
|
||||||
}
|
}
|
||||||
@ -321,7 +321,7 @@ class _AstToIrVisitor implements cdAst.AstVisitor {
|
|||||||
return convertToStatementIfNeeded(mode, o.literal(ast.value));
|
return convertToStatementIfNeeded(mode, o.literal(ast.value));
|
||||||
}
|
}
|
||||||
|
|
||||||
private _getLocal(name: string): o.Expression { return this._localResolver.getLocal(name); }
|
private _getLocal(name: string): o.Expression|null { return this._localResolver.getLocal(name); }
|
||||||
|
|
||||||
visitMethodCall(ast: cdAst.MethodCall, mode: _Mode): any {
|
visitMethodCall(ast: cdAst.MethodCall, mode: _Mode): any {
|
||||||
const leftMostSafe = this.leftMostSafeNode(ast);
|
const leftMostSafe = this.leftMostSafeNode(ast);
|
||||||
@ -439,7 +439,7 @@ class _AstToIrVisitor implements cdAst.AstVisitor {
|
|||||||
// which comes in as leftMostSafe to this routine.
|
// which comes in as leftMostSafe to this routine.
|
||||||
|
|
||||||
let guardedExpression = this.visit(leftMostSafe.receiver, _Mode.Expression);
|
let guardedExpression = this.visit(leftMostSafe.receiver, _Mode.Expression);
|
||||||
let temporary: o.ReadVarExpr;
|
let temporary: o.ReadVarExpr = undefined !;
|
||||||
if (this.needsTemporary(leftMostSafe.receiver)) {
|
if (this.needsTemporary(leftMostSafe.receiver)) {
|
||||||
// If the expression has method calls or pipes then we need to save the result into a
|
// If the expression has method calls or pipes then we need to save the result into a
|
||||||
// temporary variable to avoid calling stateful or impure code more than once.
|
// temporary variable to avoid calling stateful or impure code more than once.
|
||||||
@ -577,7 +577,7 @@ function flattenStatements(arg: any, output: o.Statement[]) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class DefaultLocalResolver implements LocalResolver {
|
class DefaultLocalResolver implements LocalResolver {
|
||||||
getLocal(name: string): o.Expression {
|
getLocal(name: string): o.Expression|null {
|
||||||
if (name === EventHandlerVars.event.name) {
|
if (name === EventHandlerVars.event.name) {
|
||||||
return EventHandlerVars.event;
|
return EventHandlerVars.event;
|
||||||
}
|
}
|
||||||
@ -593,7 +593,7 @@ function createPreventDefaultVar(bindingId: string): o.ReadVarExpr {
|
|||||||
return o.variable(`pd_${bindingId}`);
|
return o.variable(`pd_${bindingId}`);
|
||||||
}
|
}
|
||||||
|
|
||||||
function convertStmtIntoExpression(stmt: o.Statement): o.Expression {
|
function convertStmtIntoExpression(stmt: o.Statement): o.Expression|null {
|
||||||
if (stmt instanceof o.ExpressionStatement) {
|
if (stmt instanceof o.ExpressionStatement) {
|
||||||
return stmt.expr;
|
return stmt.expr;
|
||||||
} else if (stmt instanceof o.ReturnStatement) {
|
} else if (stmt instanceof o.ReturnStatement) {
|
||||||
|
@ -13,12 +13,12 @@ import {Identifiers, createIdentifier} from './identifiers';
|
|||||||
|
|
||||||
|
|
||||||
export class CompilerConfig {
|
export class CompilerConfig {
|
||||||
public defaultEncapsulation: ViewEncapsulation;
|
public defaultEncapsulation: ViewEncapsulation|null;
|
||||||
// Whether to support the `<template>` tag and the `template` attribute to define angular
|
// Whether to support the `<template>` tag and the `template` attribute to define angular
|
||||||
// templates. They have been deprecated in 4.x, `<ng-template>` should be used instead.
|
// templates. They have been deprecated in 4.x, `<ng-template>` should be used instead.
|
||||||
public enableLegacyTemplate: boolean;
|
public enableLegacyTemplate: boolean;
|
||||||
public useJit: boolean;
|
public useJit: boolean;
|
||||||
public missingTranslation: MissingTranslationStrategy;
|
public missingTranslation: MissingTranslationStrategy|null;
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
{defaultEncapsulation = ViewEncapsulation.Emulated, useJit = true, missingTranslation,
|
{defaultEncapsulation = ViewEncapsulation.Emulated, useJit = true, missingTranslation,
|
||||||
@ -29,8 +29,8 @@ export class CompilerConfig {
|
|||||||
enableLegacyTemplate?: boolean,
|
enableLegacyTemplate?: boolean,
|
||||||
} = {}) {
|
} = {}) {
|
||||||
this.defaultEncapsulation = defaultEncapsulation;
|
this.defaultEncapsulation = defaultEncapsulation;
|
||||||
this.useJit = useJit;
|
this.useJit = !!useJit;
|
||||||
this.missingTranslation = missingTranslation;
|
this.missingTranslation = missingTranslation || null;
|
||||||
this.enableLegacyTemplate = enableLegacyTemplate !== false;
|
this.enableLegacyTemplate = enableLegacyTemplate !== false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -65,7 +65,7 @@ export abstract class CssRuleAst extends CssAst {
|
|||||||
export class CssBlockRuleAst extends CssRuleAst {
|
export class CssBlockRuleAst extends CssRuleAst {
|
||||||
constructor(
|
constructor(
|
||||||
public location: ParseSourceSpan, public type: BlockType, public block: CssBlockAst,
|
public location: ParseSourceSpan, public type: BlockType, public block: CssBlockAst,
|
||||||
public name: CssToken = null) {
|
public name: CssToken|null = null) {
|
||||||
super(location);
|
super(location);
|
||||||
}
|
}
|
||||||
visit(visitor: CssAstVisitor, context?: any): any {
|
visit(visitor: CssAstVisitor, context?: any): any {
|
||||||
|
@ -40,7 +40,7 @@ export enum CssLexerMode {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class LexedCssResult {
|
export class LexedCssResult {
|
||||||
constructor(public error: Error, public token: CssToken) {}
|
constructor(public error: Error|null, public token: CssToken) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
export function generateErrorMessage(
|
export function generateErrorMessage(
|
||||||
@ -126,7 +126,7 @@ export class CssScanner {
|
|||||||
/** @internal */
|
/** @internal */
|
||||||
_currentMode: CssLexerMode = CssLexerMode.BLOCK;
|
_currentMode: CssLexerMode = CssLexerMode.BLOCK;
|
||||||
/** @internal */
|
/** @internal */
|
||||||
_currentError: Error = null;
|
_currentError: Error|null = null;
|
||||||
|
|
||||||
constructor(public input: string, private _trackComments: boolean = false) {
|
constructor(public input: string, private _trackComments: boolean = false) {
|
||||||
this.length = this.input.length;
|
this.length = this.input.length;
|
||||||
@ -188,7 +188,7 @@ export class CssScanner {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
consume(type: CssTokenType, value: string = null): LexedCssResult {
|
consume(type: CssTokenType, value: string|null = null): LexedCssResult {
|
||||||
const mode = this._currentMode;
|
const mode = this._currentMode;
|
||||||
|
|
||||||
this.setMode(_trackWhitespace(mode) ? CssLexerMode.ALL_TRACK_WS : CssLexerMode.ALL);
|
this.setMode(_trackWhitespace(mode) ? CssLexerMode.ALL_TRACK_WS : CssLexerMode.ALL);
|
||||||
@ -197,7 +197,7 @@ export class CssScanner {
|
|||||||
const previousLine = this.line;
|
const previousLine = this.line;
|
||||||
const previousColumn = this.column;
|
const previousColumn = this.column;
|
||||||
|
|
||||||
let next: CssToken;
|
let next: CssToken = undefined !;
|
||||||
const output = this.scan();
|
const output = this.scan();
|
||||||
if (output != null) {
|
if (output != null) {
|
||||||
// just incase the inner scan method returned an error
|
// just incase the inner scan method returned an error
|
||||||
@ -225,7 +225,7 @@ export class CssScanner {
|
|||||||
// mode so that the parser can recover...
|
// mode so that the parser can recover...
|
||||||
this.setMode(mode);
|
this.setMode(mode);
|
||||||
|
|
||||||
let error: Error = null;
|
let error: Error|null = null;
|
||||||
if (!isMatchingType || (value != null && value != next.strValue)) {
|
if (!isMatchingType || (value != null && value != next.strValue)) {
|
||||||
let errorMessage =
|
let errorMessage =
|
||||||
CssTokenType[next.type] + ' does not match expected ' + CssTokenType[type] + ' value';
|
CssTokenType[next.type] + ' does not match expected ' + CssTokenType[type] + ' value';
|
||||||
@ -244,7 +244,7 @@ export class CssScanner {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
scan(): LexedCssResult {
|
scan(): LexedCssResult|null {
|
||||||
const trackWS = _trackWhitespace(this._currentMode);
|
const trackWS = _trackWhitespace(this._currentMode);
|
||||||
if (this.index == 0 && !trackWS) { // first scan
|
if (this.index == 0 && !trackWS) { // first scan
|
||||||
this.consumeWhitespace();
|
this.consumeWhitespace();
|
||||||
@ -253,7 +253,7 @@ export class CssScanner {
|
|||||||
const token = this._scan();
|
const token = this._scan();
|
||||||
if (token == null) return null;
|
if (token == null) return null;
|
||||||
|
|
||||||
const error = this._currentError;
|
const error = this._currentError !;
|
||||||
this._currentError = null;
|
this._currentError = null;
|
||||||
|
|
||||||
if (!trackWS) {
|
if (!trackWS) {
|
||||||
@ -263,7 +263,7 @@ export class CssScanner {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** @internal */
|
/** @internal */
|
||||||
_scan(): CssToken {
|
_scan(): CssToken|null {
|
||||||
let peek = this.peek;
|
let peek = this.peek;
|
||||||
let peekPeek = this.peekPeek;
|
let peekPeek = this.peekPeek;
|
||||||
if (peek == chars.$EOF) return null;
|
if (peek == chars.$EOF) return null;
|
||||||
@ -317,7 +317,7 @@ export class CssScanner {
|
|||||||
return this.error(`Unexpected character [${String.fromCharCode(peek)}]`);
|
return this.error(`Unexpected character [${String.fromCharCode(peek)}]`);
|
||||||
}
|
}
|
||||||
|
|
||||||
scanComment(): CssToken {
|
scanComment(): CssToken|null {
|
||||||
if (this.assertCondition(
|
if (this.assertCondition(
|
||||||
isCommentStart(this.peek, this.peekPeek), 'Expected comment start value')) {
|
isCommentStart(this.peek, this.peekPeek), 'Expected comment start value')) {
|
||||||
return null;
|
return null;
|
||||||
@ -355,7 +355,7 @@ export class CssScanner {
|
|||||||
return new CssToken(start, startingColumn, startingLine, CssTokenType.Whitespace, str);
|
return new CssToken(start, startingColumn, startingLine, CssTokenType.Whitespace, str);
|
||||||
}
|
}
|
||||||
|
|
||||||
scanString(): CssToken {
|
scanString(): CssToken|null {
|
||||||
if (this.assertCondition(
|
if (this.assertCondition(
|
||||||
isStringStart(this.peek, this.peekPeek), 'Unexpected non-string starting value')) {
|
isStringStart(this.peek, this.peekPeek), 'Unexpected non-string starting value')) {
|
||||||
return null;
|
return null;
|
||||||
@ -405,7 +405,7 @@ export class CssScanner {
|
|||||||
return new CssToken(start, startingColumn, this.line, CssTokenType.Number, strValue);
|
return new CssToken(start, startingColumn, this.line, CssTokenType.Number, strValue);
|
||||||
}
|
}
|
||||||
|
|
||||||
scanIdentifier(): CssToken {
|
scanIdentifier(): CssToken|null {
|
||||||
if (this.assertCondition(
|
if (this.assertCondition(
|
||||||
isIdentifierStart(this.peek, this.peekPeek), 'Expected identifier starting value')) {
|
isIdentifierStart(this.peek, this.peekPeek), 'Expected identifier starting value')) {
|
||||||
return null;
|
return null;
|
||||||
@ -436,7 +436,7 @@ export class CssScanner {
|
|||||||
return new CssToken(start, startingColumn, this.line, CssTokenType.Identifier, strValue);
|
return new CssToken(start, startingColumn, this.line, CssTokenType.Identifier, strValue);
|
||||||
}
|
}
|
||||||
|
|
||||||
scanCharacter(): CssToken {
|
scanCharacter(): CssToken|null {
|
||||||
const start = this.index;
|
const start = this.index;
|
||||||
const startingColumn = this.column;
|
const startingColumn = this.column;
|
||||||
if (this.assertCondition(
|
if (this.assertCondition(
|
||||||
@ -451,7 +451,7 @@ export class CssScanner {
|
|||||||
return new CssToken(start, startingColumn, this.line, CssTokenType.Character, c);
|
return new CssToken(start, startingColumn, this.line, CssTokenType.Character, c);
|
||||||
}
|
}
|
||||||
|
|
||||||
scanAtExpression(): CssToken {
|
scanAtExpression(): CssToken|null {
|
||||||
if (this.assertCondition(this.peek == chars.$AT, 'Expected @ value')) {
|
if (this.assertCondition(this.peek == chars.$AT, 'Expected @ value')) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
@ -460,7 +460,7 @@ export class CssScanner {
|
|||||||
const startingColumn = this.column;
|
const startingColumn = this.column;
|
||||||
this.advance();
|
this.advance();
|
||||||
if (isIdentifierStart(this.peek, this.peekPeek)) {
|
if (isIdentifierStart(this.peek, this.peekPeek)) {
|
||||||
const ident = this.scanIdentifier();
|
const ident = this.scanIdentifier() !;
|
||||||
const strValue = '@' + ident.strValue;
|
const strValue = '@' + ident.strValue;
|
||||||
return new CssToken(start, startingColumn, this.line, CssTokenType.AtKeyword, strValue);
|
return new CssToken(start, startingColumn, this.line, CssTokenType.AtKeyword, strValue);
|
||||||
} else {
|
} else {
|
||||||
@ -476,7 +476,8 @@ export class CssScanner {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
error(message: string, errorTokenValue: string = null, doNotAdvance: boolean = false): CssToken {
|
error(message: string, errorTokenValue: string|null = null, doNotAdvance: boolean = false):
|
||||||
|
CssToken {
|
||||||
const index: number = this.index;
|
const index: number = this.index;
|
||||||
const column: number = this.column;
|
const column: number = this.column;
|
||||||
const line: number = this.line;
|
const line: number = this.line;
|
||||||
|
@ -102,8 +102,8 @@ export class CssParser {
|
|||||||
this._errors = [];
|
this._errors = [];
|
||||||
|
|
||||||
const result = new ParsedCssResult(errors, ast);
|
const result = new ParsedCssResult(errors, ast);
|
||||||
this._file = null;
|
this._file = null as any;
|
||||||
this._scanner = null;
|
this._scanner = null as any;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -115,14 +115,14 @@ export class CssParser {
|
|||||||
this._scanner.setMode(CssLexerMode.BLOCK);
|
this._scanner.setMode(CssLexerMode.BLOCK);
|
||||||
results.push(this._parseRule(delimiters));
|
results.push(this._parseRule(delimiters));
|
||||||
}
|
}
|
||||||
let span: ParseSourceSpan = null;
|
let span: ParseSourceSpan|null = null;
|
||||||
if (results.length > 0) {
|
if (results.length > 0) {
|
||||||
const firstRule = results[0];
|
const firstRule = results[0];
|
||||||
// we collect the last token like so incase there was an
|
// we collect the last token like so incase there was an
|
||||||
// EOF token that was emitted sometime during the lexing
|
// EOF token that was emitted sometime during the lexing
|
||||||
span = this._generateSourceSpan(firstRule, this._lastToken);
|
span = this._generateSourceSpan(firstRule, this._lastToken);
|
||||||
}
|
}
|
||||||
return new CssStyleSheetAst(span, results);
|
return new CssStyleSheetAst(span !, results);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @internal */
|
/** @internal */
|
||||||
@ -134,7 +134,7 @@ export class CssParser {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** @internal */
|
/** @internal */
|
||||||
_generateSourceSpan(start: CssToken|CssAst, end: CssToken|CssAst = null): ParseSourceSpan {
|
_generateSourceSpan(start: CssToken|CssAst, end: CssToken|CssAst|null = null): ParseSourceSpan {
|
||||||
let startLoc: ParseLocation;
|
let startLoc: ParseLocation;
|
||||||
if (start instanceof CssAst) {
|
if (start instanceof CssAst) {
|
||||||
startLoc = start.location.start;
|
startLoc = start.location.start;
|
||||||
@ -152,13 +152,13 @@ export class CssParser {
|
|||||||
end = this._lastToken;
|
end = this._lastToken;
|
||||||
}
|
}
|
||||||
|
|
||||||
let endLine: number;
|
let endLine: number = -1;
|
||||||
let endColumn: number;
|
let endColumn: number = -1;
|
||||||
let endIndex: number;
|
let endIndex: number = -1;
|
||||||
if (end instanceof CssAst) {
|
if (end instanceof CssAst) {
|
||||||
endLine = end.location.end.line;
|
endLine = end.location.end.line !;
|
||||||
endColumn = end.location.end.col;
|
endColumn = end.location.end.col !;
|
||||||
endIndex = end.location.end.offset;
|
endIndex = end.location.end.offset !;
|
||||||
} else if (end instanceof CssToken) {
|
} else if (end instanceof CssToken) {
|
||||||
endLine = end.line;
|
endLine = end.line;
|
||||||
endColumn = end.column;
|
endColumn = end.column;
|
||||||
@ -250,7 +250,7 @@ export class CssParser {
|
|||||||
|
|
||||||
case BlockType.Viewport:
|
case BlockType.Viewport:
|
||||||
case BlockType.FontFace:
|
case BlockType.FontFace:
|
||||||
block = this._parseStyleBlock(delimiters);
|
block = this._parseStyleBlock(delimiters) !;
|
||||||
span = this._generateSourceSpan(startToken, block);
|
span = this._generateSourceSpan(startToken, block);
|
||||||
return new CssBlockRuleAst(span, type, block);
|
return new CssBlockRuleAst(span, type, block);
|
||||||
|
|
||||||
@ -290,7 +290,7 @@ export class CssParser {
|
|||||||
span = this._generateSourceSpan(startToken, tokens[tokens.length - 1]);
|
span = this._generateSourceSpan(startToken, tokens[tokens.length - 1]);
|
||||||
query = new CssAtRulePredicateAst(span, strValue, tokens);
|
query = new CssAtRulePredicateAst(span, strValue, tokens);
|
||||||
block = this._parseBlock(delimiters);
|
block = this._parseBlock(delimiters);
|
||||||
strValue = this._extractSourceContent(start, block.end.offset);
|
strValue = this._extractSourceContent(start, block.end.offset !);
|
||||||
span = this._generateSourceSpan(startToken, block);
|
span = this._generateSourceSpan(startToken, block);
|
||||||
return new CssBlockDefinitionRuleAst(span, strValue, type, query, block);
|
return new CssBlockDefinitionRuleAst(span, strValue, type, query, block);
|
||||||
|
|
||||||
@ -373,7 +373,7 @@ export class CssParser {
|
|||||||
|
|
||||||
/** @internal */
|
/** @internal */
|
||||||
_scan(): CssToken {
|
_scan(): CssToken {
|
||||||
const output = this._scanner.scan();
|
const output = this._scanner.scan() !;
|
||||||
const token = output.token;
|
const token = output.token;
|
||||||
const error = output.error;
|
const error = output.error;
|
||||||
if (error != null) {
|
if (error != null) {
|
||||||
@ -387,7 +387,7 @@ export class CssParser {
|
|||||||
_getScannerIndex(): number { return this._scanner.index; }
|
_getScannerIndex(): number { return this._scanner.index; }
|
||||||
|
|
||||||
/** @internal */
|
/** @internal */
|
||||||
_consume(type: CssTokenType, value: string = null): CssToken {
|
_consume(type: CssTokenType, value: string|null = null): CssToken {
|
||||||
const output = this._scanner.consume(type, value);
|
const output = this._scanner.consume(type, value);
|
||||||
const token = output.token;
|
const token = output.token;
|
||||||
const error = output.error;
|
const error = output.error;
|
||||||
@ -429,7 +429,7 @@ export class CssParser {
|
|||||||
}
|
}
|
||||||
const stylesBlock = this._parseStyleBlock(delimiters | RBRACE_DELIM_FLAG);
|
const stylesBlock = this._parseStyleBlock(delimiters | RBRACE_DELIM_FLAG);
|
||||||
const span = this._generateSourceSpan(stepTokens[0], stylesBlock);
|
const span = this._generateSourceSpan(stepTokens[0], stylesBlock);
|
||||||
const ast = new CssKeyframeDefinitionAst(span, stepTokens, stylesBlock);
|
const ast = new CssKeyframeDefinitionAst(span, stepTokens, stylesBlock !);
|
||||||
|
|
||||||
this._scanner.setMode(CssLexerMode.BLOCK);
|
this._scanner.setMode(CssLexerMode.BLOCK);
|
||||||
return ast;
|
return ast;
|
||||||
@ -520,7 +520,7 @@ export class CssParser {
|
|||||||
const selectorCssTokens: CssToken[] = [];
|
const selectorCssTokens: CssToken[] = [];
|
||||||
const pseudoSelectors: CssPseudoSelectorAst[] = [];
|
const pseudoSelectors: CssPseudoSelectorAst[] = [];
|
||||||
|
|
||||||
let previousToken: CssToken;
|
let previousToken: CssToken = undefined !;
|
||||||
|
|
||||||
const selectorPartDelimiters = delimiters | SPACE_DELIM_FLAG;
|
const selectorPartDelimiters = delimiters | SPACE_DELIM_FLAG;
|
||||||
let loopOverSelector = !characterContainsDelimiter(this._scanner.peek, selectorPartDelimiters);
|
let loopOverSelector = !characterContainsDelimiter(this._scanner.peek, selectorPartDelimiters);
|
||||||
@ -581,9 +581,9 @@ export class CssParser {
|
|||||||
|
|
||||||
// this happens if the selector is not directly followed by
|
// this happens if the selector is not directly followed by
|
||||||
// a comma or curly brace without a space in between
|
// a comma or curly brace without a space in between
|
||||||
let operator: CssToken = null;
|
let operator: CssToken|null = null;
|
||||||
let operatorScanCount = 0;
|
let operatorScanCount = 0;
|
||||||
let lastOperatorToken: CssToken = null;
|
let lastOperatorToken: CssToken|null = null;
|
||||||
if (!characterContainsDelimiter(this._scanner.peek, delimiters)) {
|
if (!characterContainsDelimiter(this._scanner.peek, delimiters)) {
|
||||||
while (operator == null && !characterContainsDelimiter(this._scanner.peek, delimiters) &&
|
while (operator == null && !characterContainsDelimiter(this._scanner.peek, delimiters) &&
|
||||||
isSelectorOperatorCharacter(this._scanner.peek)) {
|
isSelectorOperatorCharacter(this._scanner.peek)) {
|
||||||
@ -653,8 +653,8 @@ export class CssParser {
|
|||||||
|
|
||||||
// please note that `endToken` is reassigned multiple times below
|
// please note that `endToken` is reassigned multiple times below
|
||||||
// so please do not optimize the if statements into if/elseif
|
// so please do not optimize the if statements into if/elseif
|
||||||
let startTokenOrAst: CssToken|CssAst = null;
|
let startTokenOrAst: CssToken|CssAst|null = null;
|
||||||
let endTokenOrAst: CssToken|CssAst = null;
|
let endTokenOrAst: CssToken|CssAst|null = null;
|
||||||
if (selectorCssTokens.length > 0) {
|
if (selectorCssTokens.length > 0) {
|
||||||
startTokenOrAst = startTokenOrAst || selectorCssTokens[0];
|
startTokenOrAst = startTokenOrAst || selectorCssTokens[0];
|
||||||
endTokenOrAst = selectorCssTokens[selectorCssTokens.length - 1];
|
endTokenOrAst = selectorCssTokens[selectorCssTokens.length - 1];
|
||||||
@ -668,8 +668,8 @@ export class CssParser {
|
|||||||
endTokenOrAst = operator;
|
endTokenOrAst = operator;
|
||||||
}
|
}
|
||||||
|
|
||||||
const span = this._generateSourceSpan(startTokenOrAst, endTokenOrAst);
|
const span = this._generateSourceSpan(startTokenOrAst !, endTokenOrAst);
|
||||||
return new CssSimpleSelectorAst(span, selectorCssTokens, strValue, pseudoSelectors, operator);
|
return new CssSimpleSelectorAst(span, selectorCssTokens, strValue, pseudoSelectors, operator !);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @internal */
|
/** @internal */
|
||||||
@ -698,7 +698,7 @@ export class CssParser {
|
|||||||
|
|
||||||
const tokens: CssToken[] = [];
|
const tokens: CssToken[] = [];
|
||||||
let wsStr = '';
|
let wsStr = '';
|
||||||
let previous: CssToken;
|
let previous: CssToken = undefined !;
|
||||||
while (!characterContainsDelimiter(this._scanner.peek, delimiters)) {
|
while (!characterContainsDelimiter(this._scanner.peek, delimiters)) {
|
||||||
let token: CssToken;
|
let token: CssToken;
|
||||||
if (previous != null && previous.type == CssTokenType.Identifier &&
|
if (previous != null && previous.type == CssTokenType.Identifier &&
|
||||||
@ -749,7 +749,7 @@ export class CssParser {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** @internal */
|
/** @internal */
|
||||||
_collectUntilDelim(delimiters: number, assertType: CssTokenType = null): CssToken[] {
|
_collectUntilDelim(delimiters: number, assertType: CssTokenType|null = null): CssToken[] {
|
||||||
const tokens: CssToken[] = [];
|
const tokens: CssToken[] = [];
|
||||||
while (!characterContainsDelimiter(this._scanner.peek, delimiters)) {
|
while (!characterContainsDelimiter(this._scanner.peek, delimiters)) {
|
||||||
const val = assertType != null ? this._consume(assertType) : this._scan();
|
const val = assertType != null ? this._consume(assertType) : this._scan();
|
||||||
@ -782,7 +782,7 @@ export class CssParser {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** @internal */
|
/** @internal */
|
||||||
_parseStyleBlock(delimiters: number): CssStylesBlockAst {
|
_parseStyleBlock(delimiters: number): CssStylesBlockAst|null {
|
||||||
delimiters |= RBRACE_DELIM_FLAG | LBRACE_DELIM_FLAG;
|
delimiters |= RBRACE_DELIM_FLAG | LBRACE_DELIM_FLAG;
|
||||||
|
|
||||||
this._scanner.setMode(CssLexerMode.STYLE_BLOCK);
|
this._scanner.setMode(CssLexerMode.STYLE_BLOCK);
|
||||||
@ -815,7 +815,7 @@ export class CssParser {
|
|||||||
|
|
||||||
let prop = this._consume(CssTokenType.Identifier);
|
let prop = this._consume(CssTokenType.Identifier);
|
||||||
let parseValue: boolean = false;
|
let parseValue: boolean = false;
|
||||||
let value: CssStyleValueAst = null;
|
let value: CssStyleValueAst|null = null;
|
||||||
let endToken: CssToken|CssStyleValueAst = prop;
|
let endToken: CssToken|CssStyleValueAst = prop;
|
||||||
|
|
||||||
// the colon value separates the prop from the style.
|
// the colon value separates the prop from the style.
|
||||||
@ -865,7 +865,7 @@ export class CssParser {
|
|||||||
}
|
}
|
||||||
|
|
||||||
const span = this._generateSourceSpan(prop, endToken);
|
const span = this._generateSourceSpan(prop, endToken);
|
||||||
return new CssDefinitionAst(span, prop, value);
|
return new CssDefinitionAst(span, prop, value !);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @internal */
|
/** @internal */
|
||||||
|
@ -7,6 +7,7 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
import {ViewEncapsulation, ɵstringify as stringify} from '@angular/core';
|
import {ViewEncapsulation, ɵstringify as stringify} from '@angular/core';
|
||||||
|
|
||||||
import {CompileAnimationEntryMetadata, CompileDirectiveMetadata, CompileStylesheetMetadata, CompileTemplateMetadata, templateSourceUrl} from './compile_metadata';
|
import {CompileAnimationEntryMetadata, CompileDirectiveMetadata, CompileStylesheetMetadata, CompileTemplateMetadata, templateSourceUrl} from './compile_metadata';
|
||||||
import {CompilerConfig} from './config';
|
import {CompilerConfig} from './config';
|
||||||
import {CompilerInjectable} from './injectable';
|
import {CompilerInjectable} from './injectable';
|
||||||
@ -17,19 +18,19 @@ import {ResourceLoader} from './resource_loader';
|
|||||||
import {extractStyleUrls, isStyleUrlResolvable} from './style_url_resolver';
|
import {extractStyleUrls, isStyleUrlResolvable} from './style_url_resolver';
|
||||||
import {PreparsedElementType, preparseElement} from './template_parser/template_preparser';
|
import {PreparsedElementType, preparseElement} from './template_parser/template_preparser';
|
||||||
import {UrlResolver} from './url_resolver';
|
import {UrlResolver} from './url_resolver';
|
||||||
import {SyncAsyncResult, syntaxError} from './util';
|
import {SyncAsyncResult, isDefined, syntaxError} from './util';
|
||||||
|
|
||||||
export interface PrenormalizedTemplateMetadata {
|
export interface PrenormalizedTemplateMetadata {
|
||||||
ngModuleType: any;
|
ngModuleType: any;
|
||||||
componentType: any;
|
componentType: any;
|
||||||
moduleUrl: string;
|
moduleUrl: string;
|
||||||
template?: string;
|
template: string|null;
|
||||||
templateUrl?: string;
|
templateUrl: string|null;
|
||||||
styles?: string[];
|
styles: string[];
|
||||||
styleUrls?: string[];
|
styleUrls: string[];
|
||||||
interpolation?: [string, string];
|
interpolation: [string, string]|null;
|
||||||
encapsulation?: ViewEncapsulation;
|
encapsulation: ViewEncapsulation|null;
|
||||||
animations?: CompileAnimationEntryMetadata[];
|
animations: CompileAnimationEntryMetadata[];
|
||||||
}
|
}
|
||||||
|
|
||||||
@CompilerInjectable()
|
@CompilerInjectable()
|
||||||
@ -46,15 +47,16 @@ export class DirectiveNormalizer {
|
|||||||
if (!normalizedDirective.isComponent) {
|
if (!normalizedDirective.isComponent) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
this._resourceLoaderCache.delete(normalizedDirective.template.templateUrl);
|
const template = normalizedDirective.template !;
|
||||||
normalizedDirective.template.externalStylesheets.forEach(
|
this._resourceLoaderCache.delete(template.templateUrl !);
|
||||||
(stylesheet) => { this._resourceLoaderCache.delete(stylesheet.moduleUrl); });
|
template.externalStylesheets.forEach(
|
||||||
|
(stylesheet) => { this._resourceLoaderCache.delete(stylesheet.moduleUrl !); });
|
||||||
}
|
}
|
||||||
|
|
||||||
private _fetch(url: string): Promise<string> {
|
private _fetch(url: string): Promise<string> {
|
||||||
let result = this._resourceLoaderCache.get(url);
|
let result = this._resourceLoaderCache.get(url);
|
||||||
if (!result) {
|
if (!result) {
|
||||||
result = this._resourceLoader.get(url);
|
result = this._resourceLoader.get(url) !;
|
||||||
this._resourceLoaderCache.set(url, result);
|
this._resourceLoaderCache.set(url, result);
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
@ -62,10 +64,10 @@ export class DirectiveNormalizer {
|
|||||||
|
|
||||||
normalizeTemplate(prenormData: PrenormalizedTemplateMetadata):
|
normalizeTemplate(prenormData: PrenormalizedTemplateMetadata):
|
||||||
SyncAsyncResult<CompileTemplateMetadata> {
|
SyncAsyncResult<CompileTemplateMetadata> {
|
||||||
let normalizedTemplateSync: CompileTemplateMetadata = null;
|
let normalizedTemplateSync: CompileTemplateMetadata = null !;
|
||||||
let normalizedTemplateAsync: Promise<CompileTemplateMetadata>;
|
let normalizedTemplateAsync: Promise<CompileTemplateMetadata> = undefined !;
|
||||||
if (prenormData.template != null) {
|
if (isDefined(prenormData.template)) {
|
||||||
if (prenormData.templateUrl != null) {
|
if (isDefined(prenormData.templateUrl)) {
|
||||||
throw syntaxError(
|
throw syntaxError(
|
||||||
`'${stringify(prenormData.componentType)}' component cannot define both template and templateUrl`);
|
`'${stringify(prenormData.componentType)}' component cannot define both template and templateUrl`);
|
||||||
}
|
}
|
||||||
@ -74,8 +76,8 @@ export class DirectiveNormalizer {
|
|||||||
`The template specified for component ${stringify(prenormData.componentType)} is not a string`);
|
`The template specified for component ${stringify(prenormData.componentType)} is not a string`);
|
||||||
}
|
}
|
||||||
normalizedTemplateSync = this.normalizeTemplateSync(prenormData);
|
normalizedTemplateSync = this.normalizeTemplateSync(prenormData);
|
||||||
normalizedTemplateAsync = Promise.resolve(normalizedTemplateSync);
|
normalizedTemplateAsync = Promise.resolve(normalizedTemplateSync !);
|
||||||
} else if (prenormData.templateUrl) {
|
} else if (isDefined(prenormData.templateUrl)) {
|
||||||
if (typeof prenormData.templateUrl !== 'string') {
|
if (typeof prenormData.templateUrl !== 'string') {
|
||||||
throw syntaxError(
|
throw syntaxError(
|
||||||
`The templateUrl specified for component ${stringify(prenormData.componentType)} is not a string`);
|
`The templateUrl specified for component ${stringify(prenormData.componentType)} is not a string`);
|
||||||
@ -98,12 +100,12 @@ export class DirectiveNormalizer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
normalizeTemplateSync(prenomData: PrenormalizedTemplateMetadata): CompileTemplateMetadata {
|
normalizeTemplateSync(prenomData: PrenormalizedTemplateMetadata): CompileTemplateMetadata {
|
||||||
return this.normalizeLoadedTemplate(prenomData, prenomData.template, prenomData.moduleUrl);
|
return this.normalizeLoadedTemplate(prenomData, prenomData.template !, prenomData.moduleUrl);
|
||||||
}
|
}
|
||||||
|
|
||||||
normalizeTemplateAsync(prenomData: PrenormalizedTemplateMetadata):
|
normalizeTemplateAsync(prenomData: PrenormalizedTemplateMetadata):
|
||||||
Promise<CompileTemplateMetadata> {
|
Promise<CompileTemplateMetadata> {
|
||||||
const templateUrl = this._urlResolver.resolve(prenomData.moduleUrl, prenomData.templateUrl);
|
const templateUrl = this._urlResolver.resolve(prenomData.moduleUrl, prenomData.templateUrl !);
|
||||||
return this._fetch(templateUrl)
|
return this._fetch(templateUrl)
|
||||||
.then((value) => this.normalizeLoadedTemplate(prenomData, value, templateUrl));
|
.then((value) => this.normalizeLoadedTemplate(prenomData, value, templateUrl));
|
||||||
}
|
}
|
||||||
@ -112,7 +114,7 @@ export class DirectiveNormalizer {
|
|||||||
prenormData: PrenormalizedTemplateMetadata, template: string,
|
prenormData: PrenormalizedTemplateMetadata, template: string,
|
||||||
templateAbsUrl: string): CompileTemplateMetadata {
|
templateAbsUrl: string): CompileTemplateMetadata {
|
||||||
const isInline = !!prenormData.template;
|
const isInline = !!prenormData.template;
|
||||||
const interpolationConfig = InterpolationConfig.fromArray(prenormData.interpolation);
|
const interpolationConfig = InterpolationConfig.fromArray(prenormData.interpolation !);
|
||||||
const rootNodesAndErrors = this._htmlParser.parse(
|
const rootNodesAndErrors = this._htmlParser.parse(
|
||||||
template,
|
template,
|
||||||
templateSourceUrl(
|
templateSourceUrl(
|
||||||
@ -154,7 +156,8 @@ export class DirectiveNormalizer {
|
|||||||
templateUrl: templateAbsUrl, styles, styleUrls,
|
templateUrl: templateAbsUrl, styles, styleUrls,
|
||||||
ngContentSelectors: visitor.ngContentSelectors,
|
ngContentSelectors: visitor.ngContentSelectors,
|
||||||
animations: prenormData.animations,
|
animations: prenormData.animations,
|
||||||
interpolation: prenormData.interpolation, isInline
|
interpolation: prenormData.interpolation, isInline,
|
||||||
|
externalStylesheets: []
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -193,17 +196,18 @@ export class DirectiveNormalizer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
normalizeStylesheet(stylesheet: CompileStylesheetMetadata): CompileStylesheetMetadata {
|
normalizeStylesheet(stylesheet: CompileStylesheetMetadata): CompileStylesheetMetadata {
|
||||||
|
const moduleUrl = stylesheet.moduleUrl !;
|
||||||
const allStyleUrls = stylesheet.styleUrls.filter(isStyleUrlResolvable)
|
const allStyleUrls = stylesheet.styleUrls.filter(isStyleUrlResolvable)
|
||||||
.map(url => this._urlResolver.resolve(stylesheet.moduleUrl, url));
|
.map(url => this._urlResolver.resolve(moduleUrl, url));
|
||||||
|
|
||||||
const allStyles = stylesheet.styles.map(style => {
|
const allStyles = stylesheet.styles.map(style => {
|
||||||
const styleWithImports = extractStyleUrls(this._urlResolver, stylesheet.moduleUrl, style);
|
const styleWithImports = extractStyleUrls(this._urlResolver, moduleUrl, style);
|
||||||
allStyleUrls.push(...styleWithImports.styleUrls);
|
allStyleUrls.push(...styleWithImports.styleUrls);
|
||||||
return styleWithImports.style;
|
return styleWithImports.style;
|
||||||
});
|
});
|
||||||
|
|
||||||
return new CompileStylesheetMetadata(
|
return new CompileStylesheetMetadata(
|
||||||
{styles: allStyles, styleUrls: allStyleUrls, moduleUrl: stylesheet.moduleUrl});
|
{styles: allStyles, styleUrls: allStyleUrls, moduleUrl: moduleUrl});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -30,7 +30,10 @@ export class DirectiveResolver {
|
|||||||
/**
|
/**
|
||||||
* Return {@link Directive} for a given `Type`.
|
* Return {@link Directive} for a given `Type`.
|
||||||
*/
|
*/
|
||||||
resolve(type: Type<any>, throwIfNotFound = true): Directive {
|
resolve(type: Type<any>): Directive;
|
||||||
|
resolve(type: Type<any>, throwIfNotFound: true): Directive;
|
||||||
|
resolve(type: Type<any>, throwIfNotFound: boolean): Directive|null;
|
||||||
|
resolve(type: Type<any>, throwIfNotFound = true): Directive|null {
|
||||||
const typeMetadata = this._reflector.annotations(resolveForwardRef(type));
|
const typeMetadata = this._reflector.annotations(resolveForwardRef(type));
|
||||||
if (typeMetadata) {
|
if (typeMetadata) {
|
||||||
const metadata = findLast(typeMetadata, isDirectiveMetadata);
|
const metadata = findLast(typeMetadata, isDirectiveMetadata);
|
||||||
@ -100,7 +103,7 @@ export class DirectiveResolver {
|
|||||||
return this._merge(dm, inputs, outputs, host, queries, directiveType);
|
return this._merge(dm, inputs, outputs, host, queries, directiveType);
|
||||||
}
|
}
|
||||||
|
|
||||||
private _extractPublicName(def: string) { return splitAtColon(def, [null, def])[1].trim(); }
|
private _extractPublicName(def: string) { return splitAtColon(def, [null !, def])[1].trim(); }
|
||||||
|
|
||||||
private _dedupeBindings(bindings: string[]): string[] {
|
private _dedupeBindings(bindings: string[]): string[] {
|
||||||
const names = new Set<string>();
|
const names = new Set<string>();
|
||||||
@ -166,7 +169,7 @@ function isDirectiveMetadata(type: any): type is Directive {
|
|||||||
return type instanceof Directive;
|
return type instanceof Directive;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function findLast<T>(arr: T[], condition: (value: T) => boolean): T {
|
export function findLast<T>(arr: T[], condition: (value: T) => boolean): T|null {
|
||||||
for (let i = arr.length - 1; i >= 0; i--) {
|
for (let i = arr.length - 1; i >= 0; i--) {
|
||||||
if (condition(arr[i])) {
|
if (condition(arr[i])) {
|
||||||
return arr[i];
|
return arr[i];
|
||||||
|
@ -185,7 +185,7 @@ export class SafeMethodCall extends AST {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class FunctionCall extends AST {
|
export class FunctionCall extends AST {
|
||||||
constructor(span: ParseSpan, public target: AST, public args: any[]) { super(span); }
|
constructor(span: ParseSpan, public target: AST|null, public args: any[]) { super(span); }
|
||||||
visit(visitor: AstVisitor, context: any = null): any {
|
visit(visitor: AstVisitor, context: any = null): any {
|
||||||
return visitor.visitFunctionCall(this, context);
|
return visitor.visitFunctionCall(this, context);
|
||||||
}
|
}
|
||||||
@ -193,7 +193,7 @@ export class FunctionCall extends AST {
|
|||||||
|
|
||||||
export class ASTWithSource extends AST {
|
export class ASTWithSource extends AST {
|
||||||
constructor(
|
constructor(
|
||||||
public ast: AST, public source: string, public location: string,
|
public ast: AST, public source: string|null, public location: string,
|
||||||
public errors: ParserError[]) {
|
public errors: ParserError[]) {
|
||||||
super(new ParseSpan(0, source == null ? 0 : source.length));
|
super(new ParseSpan(0, source == null ? 0 : source.length));
|
||||||
}
|
}
|
||||||
@ -248,7 +248,7 @@ export class RecursiveAstVisitor implements AstVisitor {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
visitFunctionCall(ast: FunctionCall, context: any): any {
|
visitFunctionCall(ast: FunctionCall, context: any): any {
|
||||||
ast.target.visit(this);
|
ast.target !.visit(this);
|
||||||
this.visitAll(ast.args, context);
|
this.visitAll(ast.args, context);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
@ -337,7 +337,7 @@ export class AstTransformer implements AstVisitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
visitFunctionCall(ast: FunctionCall, context: any): AST {
|
visitFunctionCall(ast: FunctionCall, context: any): AST {
|
||||||
return new FunctionCall(ast.span, ast.target.visit(this), this.visitAll(ast.args));
|
return new FunctionCall(ast.span, ast.target !.visit(this), this.visitAll(ast.args));
|
||||||
}
|
}
|
||||||
|
|
||||||
visitLiteralArray(ast: LiteralArray, context: any): AST {
|
visitLiteralArray(ast: LiteralArray, context: any): AST {
|
||||||
|
@ -76,7 +76,7 @@ export class Token {
|
|||||||
|
|
||||||
toNumber(): number { return this.type == TokenType.Number ? this.numValue : -1; }
|
toNumber(): number { return this.type == TokenType.Number ? this.numValue : -1; }
|
||||||
|
|
||||||
toString(): string {
|
toString(): string|null {
|
||||||
switch (this.type) {
|
switch (this.type) {
|
||||||
case TokenType.Character:
|
case TokenType.Character:
|
||||||
case TokenType.Identifier:
|
case TokenType.Identifier:
|
||||||
@ -137,7 +137,7 @@ class _Scanner {
|
|||||||
this.peek = ++this.index >= this.length ? chars.$EOF : this.input.charCodeAt(this.index);
|
this.peek = ++this.index >= this.length ? chars.$EOF : this.input.charCodeAt(this.index);
|
||||||
}
|
}
|
||||||
|
|
||||||
scanToken(): Token {
|
scanToken(): Token|null {
|
||||||
const input = this.input, length = this.length;
|
const input = this.input, length = this.length;
|
||||||
let peek = this.peek, index = this.index;
|
let peek = this.peek, index = this.index;
|
||||||
|
|
||||||
|
@ -90,7 +90,7 @@ export class Parser {
|
|||||||
.parseChain();
|
.parseChain();
|
||||||
}
|
}
|
||||||
|
|
||||||
private _parseQuote(input: string, location: any): AST {
|
private _parseQuote(input: string|null, location: any): AST|null {
|
||||||
if (input == null) return null;
|
if (input == null) return null;
|
||||||
const prefixSeparatorIndex = input.indexOf(':');
|
const prefixSeparatorIndex = input.indexOf(':');
|
||||||
if (prefixSeparatorIndex == -1) return null;
|
if (prefixSeparatorIndex == -1) return null;
|
||||||
@ -100,7 +100,7 @@ export class Parser {
|
|||||||
return new Quote(new ParseSpan(0, input.length), prefix, uninterpretedExpression, location);
|
return new Quote(new ParseSpan(0, input.length), prefix, uninterpretedExpression, location);
|
||||||
}
|
}
|
||||||
|
|
||||||
parseTemplateBindings(prefixToken: string, input: string, location: any):
|
parseTemplateBindings(prefixToken: string|null, input: string, location: any):
|
||||||
TemplateBindingParseResult {
|
TemplateBindingParseResult {
|
||||||
const tokens = this._lexer.tokenize(input);
|
const tokens = this._lexer.tokenize(input);
|
||||||
if (prefixToken) {
|
if (prefixToken) {
|
||||||
@ -117,7 +117,7 @@ export class Parser {
|
|||||||
|
|
||||||
parseInterpolation(
|
parseInterpolation(
|
||||||
input: string, location: any,
|
input: string, location: any,
|
||||||
interpolationConfig: InterpolationConfig = DEFAULT_INTERPOLATION_CONFIG): ASTWithSource {
|
interpolationConfig: InterpolationConfig = DEFAULT_INTERPOLATION_CONFIG): ASTWithSource|null {
|
||||||
const split = this.splitInterpolation(input, location, interpolationConfig);
|
const split = this.splitInterpolation(input, location, interpolationConfig);
|
||||||
if (split == null) return null;
|
if (split == null) return null;
|
||||||
|
|
||||||
@ -142,7 +142,8 @@ export class Parser {
|
|||||||
|
|
||||||
splitInterpolation(
|
splitInterpolation(
|
||||||
input: string, location: string,
|
input: string, location: string,
|
||||||
interpolationConfig: InterpolationConfig = DEFAULT_INTERPOLATION_CONFIG): SplitInterpolation {
|
interpolationConfig: InterpolationConfig = DEFAULT_INTERPOLATION_CONFIG): SplitInterpolation
|
||||||
|
|null {
|
||||||
const regexp = _createInterpolateRegExp(interpolationConfig);
|
const regexp = _createInterpolateRegExp(interpolationConfig);
|
||||||
const parts = input.split(regexp);
|
const parts = input.split(regexp);
|
||||||
if (parts.length <= 1) {
|
if (parts.length <= 1) {
|
||||||
@ -175,7 +176,7 @@ export class Parser {
|
|||||||
return new SplitInterpolation(strings, expressions, offsets);
|
return new SplitInterpolation(strings, expressions, offsets);
|
||||||
}
|
}
|
||||||
|
|
||||||
wrapLiteralPrimitive(input: string, location: any): ASTWithSource {
|
wrapLiteralPrimitive(input: string|null, location: any): ASTWithSource {
|
||||||
return new ASTWithSource(
|
return new ASTWithSource(
|
||||||
new LiteralPrimitive(new ParseSpan(0, input == null ? 0 : input.length), input), input,
|
new LiteralPrimitive(new ParseSpan(0, input == null ? 0 : input.length), input), input,
|
||||||
location, this.errors);
|
location, this.errors);
|
||||||
@ -186,8 +187,8 @@ export class Parser {
|
|||||||
return i != null ? input.substring(0, i).trim() : input;
|
return i != null ? input.substring(0, i).trim() : input;
|
||||||
}
|
}
|
||||||
|
|
||||||
private _commentStart(input: string): number {
|
private _commentStart(input: string): number|null {
|
||||||
let outerQuote: number = null;
|
let outerQuote: number|null = null;
|
||||||
for (let i = 0; i < input.length - 1; i++) {
|
for (let i = 0; i < input.length - 1; i++) {
|
||||||
const char = input.charCodeAt(i);
|
const char = input.charCodeAt(i);
|
||||||
const nextChar = input.charCodeAt(i + 1);
|
const nextChar = input.charCodeAt(i + 1);
|
||||||
@ -288,7 +289,7 @@ export class _ParseAST {
|
|||||||
this.error(`Missing expected operator ${operator}`);
|
this.error(`Missing expected operator ${operator}`);
|
||||||
}
|
}
|
||||||
|
|
||||||
expectIdentifierOrKeyword(): string {
|
expectIdentifierOrKeyword(): string|null {
|
||||||
const n = this.next;
|
const n = this.next;
|
||||||
if (!n.isIdentifier() && !n.isKeyword()) {
|
if (!n.isIdentifier() && !n.isKeyword()) {
|
||||||
this.error(`Unexpected token ${n}, expected identifier or keyword`);
|
this.error(`Unexpected token ${n}, expected identifier or keyword`);
|
||||||
@ -298,7 +299,7 @@ export class _ParseAST {
|
|||||||
return n.toString();
|
return n.toString();
|
||||||
}
|
}
|
||||||
|
|
||||||
expectIdentifierOrKeywordOrString(): string {
|
expectIdentifierOrKeywordOrString(): string|null {
|
||||||
const n = this.next;
|
const n = this.next;
|
||||||
if (!n.isIdentifier() && !n.isKeyword() && !n.isString()) {
|
if (!n.isIdentifier() && !n.isKeyword() && !n.isString()) {
|
||||||
this.error(`Unexpected token ${n}, expected identifier, keyword, or string`);
|
this.error(`Unexpected token ${n}, expected identifier, keyword, or string`);
|
||||||
@ -338,7 +339,7 @@ export class _ParseAST {
|
|||||||
}
|
}
|
||||||
|
|
||||||
do {
|
do {
|
||||||
const name = this.expectIdentifierOrKeyword();
|
const name = this.expectIdentifierOrKeyword() !;
|
||||||
const args: AST[] = [];
|
const args: AST[] = [];
|
||||||
while (this.optionalCharacter(chars.$COLON)) {
|
while (this.optionalCharacter(chars.$COLON)) {
|
||||||
args.push(this.parseExpression());
|
args.push(this.parseExpression());
|
||||||
@ -607,7 +608,7 @@ export class _ParseAST {
|
|||||||
if (!this.optionalCharacter(chars.$RBRACE)) {
|
if (!this.optionalCharacter(chars.$RBRACE)) {
|
||||||
this.rbracesExpected++;
|
this.rbracesExpected++;
|
||||||
do {
|
do {
|
||||||
const key = this.expectIdentifierOrKeywordOrString();
|
const key = this.expectIdentifierOrKeywordOrString() !;
|
||||||
keys.push(key);
|
keys.push(key);
|
||||||
this.expectCharacter(chars.$COLON);
|
this.expectCharacter(chars.$COLON);
|
||||||
values.push(this.parsePipe());
|
values.push(this.parsePipe());
|
||||||
@ -620,7 +621,7 @@ export class _ParseAST {
|
|||||||
|
|
||||||
parseAccessMemberOrMethodCall(receiver: AST, isSafe: boolean = false): AST {
|
parseAccessMemberOrMethodCall(receiver: AST, isSafe: boolean = false): AST {
|
||||||
const start = receiver.span.start;
|
const start = receiver.span.start;
|
||||||
const id = this.expectIdentifierOrKeyword();
|
const id = this.expectIdentifierOrKeyword() !;
|
||||||
|
|
||||||
if (this.optionalCharacter(chars.$LPAREN)) {
|
if (this.optionalCharacter(chars.$LPAREN)) {
|
||||||
this.rparensExpected++;
|
this.rparensExpected++;
|
||||||
@ -683,7 +684,7 @@ export class _ParseAST {
|
|||||||
|
|
||||||
parseTemplateBindings(): TemplateBindingParseResult {
|
parseTemplateBindings(): TemplateBindingParseResult {
|
||||||
const bindings: TemplateBinding[] = [];
|
const bindings: TemplateBinding[] = [];
|
||||||
let prefix: string = null;
|
let prefix: string = null !;
|
||||||
const warnings: string[] = [];
|
const warnings: string[] = [];
|
||||||
while (this.index < this.tokens.length) {
|
while (this.index < this.tokens.length) {
|
||||||
const start = this.inputIndex;
|
const start = this.inputIndex;
|
||||||
@ -701,8 +702,8 @@ export class _ParseAST {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
this.optionalCharacter(chars.$COLON);
|
this.optionalCharacter(chars.$COLON);
|
||||||
let name: string = null;
|
let name: string = null !;
|
||||||
let expression: ASTWithSource = null;
|
let expression: ASTWithSource = null !;
|
||||||
if (keyIsVar) {
|
if (keyIsVar) {
|
||||||
if (this.optionalOperator('=')) {
|
if (this.optionalOperator('=')) {
|
||||||
name = this.expectTemplateBindingKey();
|
name = this.expectTemplateBindingKey();
|
||||||
@ -726,7 +727,7 @@ export class _ParseAST {
|
|||||||
const letStart = this.inputIndex;
|
const letStart = this.inputIndex;
|
||||||
this.advance(); // consume `as`
|
this.advance(); // consume `as`
|
||||||
const letName = this.expectTemplateBindingKey(); // read local var name
|
const letName = this.expectTemplateBindingKey(); // read local var name
|
||||||
bindings.push(new TemplateBinding(this.span(letStart), letName, true, key, null));
|
bindings.push(new TemplateBinding(this.span(letStart), letName, true, key, null !));
|
||||||
}
|
}
|
||||||
if (!this.optionalCharacter(chars.$SEMICOLON)) {
|
if (!this.optionalCharacter(chars.$SEMICOLON)) {
|
||||||
this.optionalCharacter(chars.$COMMA);
|
this.optionalCharacter(chars.$COMMA);
|
||||||
@ -735,12 +736,12 @@ export class _ParseAST {
|
|||||||
return new TemplateBindingParseResult(bindings, warnings, this.errors);
|
return new TemplateBindingParseResult(bindings, warnings, this.errors);
|
||||||
}
|
}
|
||||||
|
|
||||||
error(message: string, index: number = null) {
|
error(message: string, index: number|null = null) {
|
||||||
this.errors.push(new ParserError(message, this.input, this.locationText(index), this.location));
|
this.errors.push(new ParserError(message, this.input, this.locationText(index), this.location));
|
||||||
this.skip();
|
this.skip();
|
||||||
}
|
}
|
||||||
|
|
||||||
private locationText(index: number = null) {
|
private locationText(index: number|null = null) {
|
||||||
if (index == null) index = this.index;
|
if (index == null) index = this.index;
|
||||||
return (index < this.tokens.length) ? `at column ${this.tokens[index].index + 1} in` :
|
return (index < this.tokens.length) ? `at column ${this.tokens[index].index + 1} in` :
|
||||||
`at the end of the expression`;
|
`at the end of the expression`;
|
||||||
@ -766,8 +767,8 @@ export class _ParseAST {
|
|||||||
(this.rbracesExpected <= 0 || !n.isCharacter(chars.$RBRACE)) &&
|
(this.rbracesExpected <= 0 || !n.isCharacter(chars.$RBRACE)) &&
|
||||||
(this.rbracketsExpected <= 0 || !n.isCharacter(chars.$RBRACKET))) {
|
(this.rbracketsExpected <= 0 || !n.isCharacter(chars.$RBRACKET))) {
|
||||||
if (this.next.isError()) {
|
if (this.next.isError()) {
|
||||||
this.errors.push(
|
this.errors.push(new ParserError(
|
||||||
new ParserError(this.next.toString(), this.input, this.locationText(), this.location));
|
this.next.toString() !, this.input, this.locationText(), this.location));
|
||||||
}
|
}
|
||||||
this.advance();
|
this.advance();
|
||||||
n = this.next;
|
n = this.next;
|
||||||
|
@ -70,11 +70,11 @@ export class Extractor {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
compMetas.forEach(compMeta => {
|
compMetas.forEach(compMeta => {
|
||||||
const html = compMeta.template.template;
|
const html = compMeta.template !.template !;
|
||||||
const interpolationConfig =
|
const interpolationConfig =
|
||||||
InterpolationConfig.fromArray(compMeta.template.interpolation);
|
InterpolationConfig.fromArray(compMeta.template !.interpolation);
|
||||||
errors.push(
|
errors.push(...this.messageBundle.updateFromTemplate(
|
||||||
...this.messageBundle.updateFromTemplate(html, file.srcUrl, interpolationConfig));
|
html, file.srcUrl, interpolationConfig) !);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -71,7 +71,7 @@ class _Visitor implements html.Visitor {
|
|||||||
private _inIcu: boolean;
|
private _inIcu: boolean;
|
||||||
|
|
||||||
// set to void 0 when not in a section
|
// set to void 0 when not in a section
|
||||||
private _msgCountAtSectionStart: number;
|
private _msgCountAtSectionStart: number|undefined;
|
||||||
private _errors: I18nError[];
|
private _errors: I18nError[];
|
||||||
private _mode: _VisitorMode;
|
private _mode: _VisitorMode;
|
||||||
|
|
||||||
@ -111,7 +111,7 @@ class _Visitor implements html.Visitor {
|
|||||||
this._translations = translations;
|
this._translations = translations;
|
||||||
|
|
||||||
// Construct a single fake root element
|
// Construct a single fake root element
|
||||||
const wrapper = new html.Element('wrapper', [], nodes, null, null, null);
|
const wrapper = new html.Element('wrapper', [], nodes, undefined, undefined, undefined);
|
||||||
|
|
||||||
const translatedNode = wrapper.visit(this, null);
|
const translatedNode = wrapper.visit(this, null);
|
||||||
|
|
||||||
@ -179,7 +179,8 @@ class _Visitor implements html.Visitor {
|
|||||||
this._inI18nBlock = true;
|
this._inI18nBlock = true;
|
||||||
this._blockStartDepth = this._depth;
|
this._blockStartDepth = this._depth;
|
||||||
this._blockChildren = [];
|
this._blockChildren = [];
|
||||||
this._blockMeaningAndDesc = comment.value.replace(_I18N_COMMENT_PREFIX_REGEXP, '').trim();
|
this._blockMeaningAndDesc =
|
||||||
|
comment.value !.replace(_I18N_COMMENT_PREFIX_REGEXP, '').trim();
|
||||||
this._openTranslatableSection(comment);
|
this._openTranslatableSection(comment);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@ -187,7 +188,7 @@ class _Visitor implements html.Visitor {
|
|||||||
if (this._depth == this._blockStartDepth) {
|
if (this._depth == this._blockStartDepth) {
|
||||||
this._closeTranslatableSection(comment, this._blockChildren);
|
this._closeTranslatableSection(comment, this._blockChildren);
|
||||||
this._inI18nBlock = false;
|
this._inI18nBlock = false;
|
||||||
const message = this._addMessage(this._blockChildren, this._blockMeaningAndDesc);
|
const message = this._addMessage(this._blockChildren, this._blockMeaningAndDesc) !;
|
||||||
// merge attributes in sections
|
// merge attributes in sections
|
||||||
const nodes = this._translateMessage(comment, message);
|
const nodes = this._translateMessage(comment, message);
|
||||||
return html.visitAll(this, nodes);
|
return html.visitAll(this, nodes);
|
||||||
@ -207,13 +208,13 @@ class _Visitor implements html.Visitor {
|
|||||||
return text;
|
return text;
|
||||||
}
|
}
|
||||||
|
|
||||||
visitElement(el: html.Element, context: any): html.Element {
|
visitElement(el: html.Element, context: any): html.Element|null {
|
||||||
this._mayBeAddBlockChildren(el);
|
this._mayBeAddBlockChildren(el);
|
||||||
this._depth++;
|
this._depth++;
|
||||||
const wasInI18nNode = this._inI18nNode;
|
const wasInI18nNode = this._inI18nNode;
|
||||||
const wasInImplicitNode = this._inImplicitNode;
|
const wasInImplicitNode = this._inImplicitNode;
|
||||||
let childNodes: html.Node[] = [];
|
let childNodes: html.Node[] = [];
|
||||||
let translatedChildNodes: html.Node[];
|
let translatedChildNodes: html.Node[] = undefined !;
|
||||||
|
|
||||||
// Extract:
|
// Extract:
|
||||||
// - top level nodes with the (implicit) "i18n" attribute if not already in a section
|
// - top level nodes with the (implicit) "i18n" attribute if not already in a section
|
||||||
@ -228,7 +229,7 @@ class _Visitor implements html.Visitor {
|
|||||||
if (!this._isInTranslatableSection && !this._inIcu) {
|
if (!this._isInTranslatableSection && !this._inIcu) {
|
||||||
if (i18nAttr || isTopLevelImplicit) {
|
if (i18nAttr || isTopLevelImplicit) {
|
||||||
this._inI18nNode = true;
|
this._inI18nNode = true;
|
||||||
const message = this._addMessage(el.children, i18nMeta);
|
const message = this._addMessage(el.children, i18nMeta) !;
|
||||||
translatedChildNodes = this._translateMessage(el, message);
|
translatedChildNodes = this._translateMessage(el, message);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -274,6 +275,7 @@ class _Visitor implements html.Visitor {
|
|||||||
el.name, translatedAttrs, childNodes, el.sourceSpan, el.startSourceSpan,
|
el.name, translatedAttrs, childNodes, el.sourceSpan, el.startSourceSpan,
|
||||||
el.endSourceSpan);
|
el.endSourceSpan);
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
visitAttribute(attribute: html.Attribute, context: any): any {
|
visitAttribute(attribute: html.Attribute, context: any): any {
|
||||||
@ -286,7 +288,7 @@ class _Visitor implements html.Visitor {
|
|||||||
this._inI18nNode = false;
|
this._inI18nNode = false;
|
||||||
this._depth = 0;
|
this._depth = 0;
|
||||||
this._inIcu = false;
|
this._inIcu = false;
|
||||||
this._msgCountAtSectionStart = void 0;
|
this._msgCountAtSectionStart = undefined;
|
||||||
this._errors = [];
|
this._errors = [];
|
||||||
this._messages = [];
|
this._messages = [];
|
||||||
this._inImplicitNode = false;
|
this._inImplicitNode = false;
|
||||||
@ -313,11 +315,11 @@ class _Visitor implements html.Visitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// add a translatable message
|
// add a translatable message
|
||||||
private _addMessage(ast: html.Node[], msgMeta?: string): i18n.Message {
|
private _addMessage(ast: html.Node[], msgMeta?: string): i18n.Message|null {
|
||||||
if (ast.length == 0 ||
|
if (ast.length == 0 ||
|
||||||
ast.length == 1 && ast[0] instanceof html.Attribute && !(<html.Attribute>ast[0]).value) {
|
ast.length == 1 && ast[0] instanceof html.Attribute && !(<html.Attribute>ast[0]).value) {
|
||||||
// Do not create empty messages
|
// Do not create empty messages
|
||||||
return;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
const {meaning, description, id} = _parseMessageMeta(msgMeta);
|
const {meaning, description, id} = _parseMessageMeta(msgMeta);
|
||||||
@ -463,27 +465,27 @@ class _Visitor implements html.Visitor {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
this._msgCountAtSectionStart = void 0;
|
this._msgCountAtSectionStart = undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
private _reportError(node: html.Node, msg: string): void {
|
private _reportError(node: html.Node, msg: string): void {
|
||||||
this._errors.push(new I18nError(node.sourceSpan, msg));
|
this._errors.push(new I18nError(node.sourceSpan !, msg));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function _isOpeningComment(n: html.Node): boolean {
|
function _isOpeningComment(n: html.Node): boolean {
|
||||||
return n instanceof html.Comment && n.value && n.value.startsWith('i18n');
|
return !!(n instanceof html.Comment && n.value && n.value.startsWith('i18n'));
|
||||||
}
|
}
|
||||||
|
|
||||||
function _isClosingComment(n: html.Node): boolean {
|
function _isClosingComment(n: html.Node): boolean {
|
||||||
return n instanceof html.Comment && n.value && n.value === '/i18n';
|
return !!(n instanceof html.Comment && n.value && n.value === '/i18n');
|
||||||
}
|
}
|
||||||
|
|
||||||
function _getI18nAttr(p: html.Element): html.Attribute {
|
function _getI18nAttr(p: html.Element): html.Attribute|null {
|
||||||
return p.attrs.find(attr => attr.name === _I18N_ATTR) || null;
|
return p.attrs.find(attr => attr.name === _I18N_ATTR) || null;
|
||||||
}
|
}
|
||||||
|
|
||||||
function _parseMessageMeta(i18n: string): {meaning: string, description: string, id: string} {
|
function _parseMessageMeta(i18n?: string): {meaning: string, description: string, id: string} {
|
||||||
if (!i18n) return {meaning: '', description: '', id: ''};
|
if (!i18n) return {meaning: '', description: '', id: ''};
|
||||||
|
|
||||||
const idIndex = i18n.indexOf(ID_SEPARATOR);
|
const idIndex = i18n.indexOf(ID_SEPARATOR);
|
||||||
|
@ -65,7 +65,7 @@ class _I18nVisitor implements html.Visitor {
|
|||||||
const isVoid: boolean = getHtmlTagDefinition(el.name).isVoid;
|
const isVoid: boolean = getHtmlTagDefinition(el.name).isVoid;
|
||||||
const startPhName =
|
const startPhName =
|
||||||
this._placeholderRegistry.getStartTagPlaceholderName(el.name, attrs, isVoid);
|
this._placeholderRegistry.getStartTagPlaceholderName(el.name, attrs, isVoid);
|
||||||
this._placeholderToContent[startPhName] = el.sourceSpan.toString();
|
this._placeholderToContent[startPhName] = el.sourceSpan !.toString();
|
||||||
|
|
||||||
let closePhName = '';
|
let closePhName = '';
|
||||||
|
|
||||||
@ -75,7 +75,7 @@ class _I18nVisitor implements html.Visitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
return new i18n.TagPlaceholder(
|
return new i18n.TagPlaceholder(
|
||||||
el.name, attrs, startPhName, closePhName, children, isVoid, el.sourceSpan);
|
el.name, attrs, startPhName, closePhName, children, isVoid, el.sourceSpan !);
|
||||||
}
|
}
|
||||||
|
|
||||||
visitAttribute(attribute: html.Attribute, context: any): i18n.Node {
|
visitAttribute(attribute: html.Attribute, context: any): i18n.Node {
|
||||||
@ -83,10 +83,10 @@ class _I18nVisitor implements html.Visitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
visitText(text: html.Text, context: any): i18n.Node {
|
visitText(text: html.Text, context: any): i18n.Node {
|
||||||
return this._visitTextWithInterpolation(text.value, text.sourceSpan);
|
return this._visitTextWithInterpolation(text.value, text.sourceSpan !);
|
||||||
}
|
}
|
||||||
|
|
||||||
visitComment(comment: html.Comment, context: any): i18n.Node { return null; }
|
visitComment(comment: html.Comment, context: any): i18n.Node|null { return null; }
|
||||||
|
|
||||||
visitExpansion(icu: html.Expansion, context: any): i18n.Node {
|
visitExpansion(icu: html.Expansion, context: any): i18n.Node {
|
||||||
this._icuDepth++;
|
this._icuDepth++;
|
||||||
|
@ -26,7 +26,7 @@ export class MessageBundle {
|
|||||||
private _implicitAttrs: {[k: string]: string[]}, private _locale: string|null = null) {}
|
private _implicitAttrs: {[k: string]: string[]}, private _locale: string|null = null) {}
|
||||||
|
|
||||||
updateFromTemplate(html: string, url: string, interpolationConfig: InterpolationConfig):
|
updateFromTemplate(html: string, url: string, interpolationConfig: InterpolationConfig):
|
||||||
ParseError[] {
|
ParseError[]|null {
|
||||||
const htmlParserResult = this._htmlParser.parse(html, url, true, interpolationConfig);
|
const htmlParserResult = this._htmlParser.parse(html, url, true, interpolationConfig);
|
||||||
|
|
||||||
if (htmlParserResult.errors.length) {
|
if (htmlParserResult.errors.length) {
|
||||||
@ -41,6 +41,7 @@ export class MessageBundle {
|
|||||||
}
|
}
|
||||||
|
|
||||||
this._messages.push(...i18nParserResult.messages);
|
this._messages.push(...i18nParserResult.messages);
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Return the message in the internal format
|
// Return the message in the internal format
|
||||||
@ -78,18 +79,18 @@ class MapPlaceholderNames extends i18n.CloneVisitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
visitTagPlaceholder(ph: i18n.TagPlaceholder, mapper: PlaceholderMapper): i18n.TagPlaceholder {
|
visitTagPlaceholder(ph: i18n.TagPlaceholder, mapper: PlaceholderMapper): i18n.TagPlaceholder {
|
||||||
const startName = mapper.toPublicName(ph.startName);
|
const startName = mapper.toPublicName(ph.startName) !;
|
||||||
const closeName = ph.closeName ? mapper.toPublicName(ph.closeName) : ph.closeName;
|
const closeName = ph.closeName ? mapper.toPublicName(ph.closeName) ! : ph.closeName;
|
||||||
const children = ph.children.map(n => n.visit(this, mapper));
|
const children = ph.children.map(n => n.visit(this, mapper));
|
||||||
return new i18n.TagPlaceholder(
|
return new i18n.TagPlaceholder(
|
||||||
ph.tag, ph.attrs, startName, closeName, children, ph.isVoid, ph.sourceSpan);
|
ph.tag, ph.attrs, startName, closeName, children, ph.isVoid, ph.sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
visitPlaceholder(ph: i18n.Placeholder, mapper: PlaceholderMapper): i18n.Placeholder {
|
visitPlaceholder(ph: i18n.Placeholder, mapper: PlaceholderMapper): i18n.Placeholder {
|
||||||
return new i18n.Placeholder(ph.value, mapper.toPublicName(ph.name), ph.sourceSpan);
|
return new i18n.Placeholder(ph.value, mapper.toPublicName(ph.name) !, ph.sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
visitIcuPlaceholder(ph: i18n.IcuPlaceholder, mapper: PlaceholderMapper): i18n.IcuPlaceholder {
|
visitIcuPlaceholder(ph: i18n.IcuPlaceholder, mapper: PlaceholderMapper): i18n.IcuPlaceholder {
|
||||||
return new i18n.IcuPlaceholder(ph.value, mapper.toPublicName(ph.name), ph.sourceSpan);
|
return new i18n.IcuPlaceholder(ph.value, mapper.toPublicName(ph.name) !, ph.sourceSpan);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -21,7 +21,7 @@ export abstract class Serializer {
|
|||||||
|
|
||||||
// Creates a name mapper, see `PlaceholderMapper`
|
// Creates a name mapper, see `PlaceholderMapper`
|
||||||
// Returning `null` means that no name mapping is used.
|
// Returning `null` means that no name mapping is used.
|
||||||
createNameMapper(message: i18n.Message): PlaceholderMapper { return null; }
|
createNameMapper(message: i18n.Message): PlaceholderMapper|null { return null; }
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -31,9 +31,9 @@ export abstract class Serializer {
|
|||||||
* It should be used for serialization format that put constraints on the placeholder names.
|
* It should be used for serialization format that put constraints on the placeholder names.
|
||||||
*/
|
*/
|
||||||
export interface PlaceholderMapper {
|
export interface PlaceholderMapper {
|
||||||
toPublicName(internalName: string): string;
|
toPublicName(internalName: string): string|null;
|
||||||
|
|
||||||
toInternalName(publicName: string): string;
|
toInternalName(publicName: string): string|null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -50,13 +50,13 @@ export class SimplePlaceholderMapper extends i18n.RecurseVisitor implements Plac
|
|||||||
message.nodes.forEach(node => node.visit(this));
|
message.nodes.forEach(node => node.visit(this));
|
||||||
}
|
}
|
||||||
|
|
||||||
toPublicName(internalName: string): string {
|
toPublicName(internalName: string): string|null {
|
||||||
return this.internalToPublic.hasOwnProperty(internalName) ?
|
return this.internalToPublic.hasOwnProperty(internalName) ?
|
||||||
this.internalToPublic[internalName] :
|
this.internalToPublic[internalName] :
|
||||||
null;
|
null;
|
||||||
}
|
}
|
||||||
|
|
||||||
toInternalName(publicName: string): string {
|
toInternalName(publicName: string): string|null {
|
||||||
return this.publicToInternal.hasOwnProperty(publicName) ? this.publicToInternal[publicName] :
|
return this.publicToInternal.hasOwnProperty(publicName) ? this.publicToInternal[publicName] :
|
||||||
null;
|
null;
|
||||||
}
|
}
|
||||||
|
@ -93,7 +93,7 @@ export class Xliff extends Serializer {
|
|||||||
throw new Error(`xliff parse errors:\n${errors.join('\n')}`);
|
throw new Error(`xliff parse errors:\n${errors.join('\n')}`);
|
||||||
}
|
}
|
||||||
|
|
||||||
return {locale, i18nNodesByMsgId};
|
return {locale: locale !, i18nNodesByMsgId};
|
||||||
}
|
}
|
||||||
|
|
||||||
digest(message: i18n.Message): string { return digest(message); }
|
digest(message: i18n.Message): string { return digest(message); }
|
||||||
@ -150,7 +150,7 @@ class _WriteVisitor implements i18n.Visitor {
|
|||||||
// TODO(vicb): add error management (structure)
|
// TODO(vicb): add error management (structure)
|
||||||
// Extract messages as xml nodes from the xliff file
|
// Extract messages as xml nodes from the xliff file
|
||||||
class XliffParser implements ml.Visitor {
|
class XliffParser implements ml.Visitor {
|
||||||
private _unitMlString: string;
|
private _unitMlString: string|null;
|
||||||
private _errors: I18nError[];
|
private _errors: I18nError[];
|
||||||
private _msgIdToHtml: {[msgId: string]: string};
|
private _msgIdToHtml: {[msgId: string]: string};
|
||||||
private _locale: string|null = null;
|
private _locale: string|null = null;
|
||||||
@ -174,7 +174,7 @@ class XliffParser implements ml.Visitor {
|
|||||||
visitElement(element: ml.Element, context: any): any {
|
visitElement(element: ml.Element, context: any): any {
|
||||||
switch (element.name) {
|
switch (element.name) {
|
||||||
case _UNIT_TAG:
|
case _UNIT_TAG:
|
||||||
this._unitMlString = null;
|
this._unitMlString = null !;
|
||||||
const idAttr = element.attrs.find((attr) => attr.name === 'id');
|
const idAttr = element.attrs.find((attr) => attr.name === 'id');
|
||||||
if (!idAttr) {
|
if (!idAttr) {
|
||||||
this._addError(element, `<${_UNIT_TAG}> misses the "id" attribute`);
|
this._addError(element, `<${_UNIT_TAG}> misses the "id" attribute`);
|
||||||
@ -198,9 +198,9 @@ class XliffParser implements ml.Visitor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case _TARGET_TAG:
|
case _TARGET_TAG:
|
||||||
const innerTextStart = element.startSourceSpan.end.offset;
|
const innerTextStart = element.startSourceSpan !.end.offset;
|
||||||
const innerTextEnd = element.endSourceSpan.start.offset;
|
const innerTextEnd = element.endSourceSpan !.start.offset;
|
||||||
const content = element.startSourceSpan.start.file.content;
|
const content = element.startSourceSpan !.start.file.content;
|
||||||
const innerText = content.slice(innerTextStart, innerTextEnd);
|
const innerText = content.slice(innerTextStart, innerTextEnd);
|
||||||
this._unitMlString = innerText;
|
this._unitMlString = innerText;
|
||||||
break;
|
break;
|
||||||
@ -231,7 +231,7 @@ class XliffParser implements ml.Visitor {
|
|||||||
visitExpansionCase(expansionCase: ml.ExpansionCase, context: any): any {}
|
visitExpansionCase(expansionCase: ml.ExpansionCase, context: any): any {}
|
||||||
|
|
||||||
private _addError(node: ml.Node, message: string): void {
|
private _addError(node: ml.Node, message: string): void {
|
||||||
this._errors.push(new I18nError(node.sourceSpan, message));
|
this._errors.push(new I18nError(node.sourceSpan !, message));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -253,19 +253,20 @@ class XmlToI18n implements ml.Visitor {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
visitText(text: ml.Text, context: any) { return new i18n.Text(text.value, text.sourceSpan); }
|
visitText(text: ml.Text, context: any) { return new i18n.Text(text.value, text.sourceSpan !); }
|
||||||
|
|
||||||
visitElement(el: ml.Element, context: any): i18n.Placeholder {
|
visitElement(el: ml.Element, context: any): i18n.Placeholder|null {
|
||||||
if (el.name === _PLACEHOLDER_TAG) {
|
if (el.name === _PLACEHOLDER_TAG) {
|
||||||
const nameAttr = el.attrs.find((attr) => attr.name === 'id');
|
const nameAttr = el.attrs.find((attr) => attr.name === 'id');
|
||||||
if (nameAttr) {
|
if (nameAttr) {
|
||||||
return new i18n.Placeholder('', nameAttr.value, el.sourceSpan);
|
return new i18n.Placeholder('', nameAttr.value, el.sourceSpan !);
|
||||||
}
|
}
|
||||||
|
|
||||||
this._addError(el, `<${_PLACEHOLDER_TAG}> misses the "id" attribute`);
|
this._addError(el, `<${_PLACEHOLDER_TAG}> misses the "id" attribute`);
|
||||||
} else {
|
} else {
|
||||||
this._addError(el, `Unexpected tag`);
|
this._addError(el, `Unexpected tag`);
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
visitExpansion(icu: ml.Expansion, context: any) {
|
visitExpansion(icu: ml.Expansion, context: any) {
|
||||||
@ -290,7 +291,7 @@ class XmlToI18n implements ml.Visitor {
|
|||||||
visitAttribute(attribute: ml.Attribute, context: any) {}
|
visitAttribute(attribute: ml.Attribute, context: any) {}
|
||||||
|
|
||||||
private _addError(node: ml.Node, message: string): void {
|
private _addError(node: ml.Node, message: string): void {
|
||||||
this._errors.push(new I18nError(node.sourceSpan, message));
|
this._errors.push(new I18nError(node.sourceSpan !, message));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -49,7 +49,7 @@ export class Xtb extends Serializer {
|
|||||||
throw new Error(`xtb parse errors:\n${errors.join('\n')}`);
|
throw new Error(`xtb parse errors:\n${errors.join('\n')}`);
|
||||||
}
|
}
|
||||||
|
|
||||||
return {locale, i18nNodesByMsgId};
|
return {locale: locale !, i18nNodesByMsgId};
|
||||||
}
|
}
|
||||||
|
|
||||||
digest(message: i18n.Message): string { return digest(message); }
|
digest(message: i18n.Message): string { return digest(message); }
|
||||||
@ -121,10 +121,10 @@ class XtbParser implements ml.Visitor {
|
|||||||
if (this._msgIdToHtml.hasOwnProperty(id)) {
|
if (this._msgIdToHtml.hasOwnProperty(id)) {
|
||||||
this._addError(element, `Duplicated translations for msg ${id}`);
|
this._addError(element, `Duplicated translations for msg ${id}`);
|
||||||
} else {
|
} else {
|
||||||
const innerTextStart = element.startSourceSpan.end.offset;
|
const innerTextStart = element.startSourceSpan !.end.offset;
|
||||||
const innerTextEnd = element.endSourceSpan.start.offset;
|
const innerTextEnd = element.endSourceSpan !.start.offset;
|
||||||
const content = element.startSourceSpan.start.file.content;
|
const content = element.startSourceSpan !.start.file.content;
|
||||||
const innerText = content.slice(innerTextStart, innerTextEnd);
|
const innerText = content.slice(innerTextStart !, innerTextEnd !);
|
||||||
this._msgIdToHtml[id] = innerText;
|
this._msgIdToHtml[id] = innerText;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -146,7 +146,7 @@ class XtbParser implements ml.Visitor {
|
|||||||
visitExpansionCase(expansionCase: ml.ExpansionCase, context: any): any {}
|
visitExpansionCase(expansionCase: ml.ExpansionCase, context: any): any {}
|
||||||
|
|
||||||
private _addError(node: ml.Node, message: string): void {
|
private _addError(node: ml.Node, message: string): void {
|
||||||
this._errors.push(new I18nError(node.sourceSpan, message));
|
this._errors.push(new I18nError(node.sourceSpan !, message));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -168,7 +168,7 @@ class XmlToI18n implements ml.Visitor {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
visitText(text: ml.Text, context: any) { return new i18n.Text(text.value, text.sourceSpan); }
|
visitText(text: ml.Text, context: any) { return new i18n.Text(text.value, text.sourceSpan !); }
|
||||||
|
|
||||||
visitExpansion(icu: ml.Expansion, context: any) {
|
visitExpansion(icu: ml.Expansion, context: any) {
|
||||||
const caseMap: {[value: string]: i18n.Node} = {};
|
const caseMap: {[value: string]: i18n.Node} = {};
|
||||||
@ -187,17 +187,18 @@ class XmlToI18n implements ml.Visitor {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
visitElement(el: ml.Element, context: any): i18n.Placeholder {
|
visitElement(el: ml.Element, context: any): i18n.Placeholder|null {
|
||||||
if (el.name === _PLACEHOLDER_TAG) {
|
if (el.name === _PLACEHOLDER_TAG) {
|
||||||
const nameAttr = el.attrs.find((attr) => attr.name === 'name');
|
const nameAttr = el.attrs.find((attr) => attr.name === 'name');
|
||||||
if (nameAttr) {
|
if (nameAttr) {
|
||||||
return new i18n.Placeholder('', nameAttr.value, el.sourceSpan);
|
return new i18n.Placeholder('', nameAttr.value, el.sourceSpan !);
|
||||||
}
|
}
|
||||||
|
|
||||||
this._addError(el, `<${_PLACEHOLDER_TAG}> misses the "name" attribute`);
|
this._addError(el, `<${_PLACEHOLDER_TAG}> misses the "name" attribute`);
|
||||||
} else {
|
} else {
|
||||||
this._addError(el, `Unexpected tag`);
|
this._addError(el, `Unexpected tag`);
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
visitComment(comment: ml.Comment, context: any) {}
|
visitComment(comment: ml.Comment, context: any) {}
|
||||||
@ -205,6 +206,6 @@ class XmlToI18n implements ml.Visitor {
|
|||||||
visitAttribute(attribute: ml.Attribute, context: any) {}
|
visitAttribute(attribute: ml.Attribute, context: any) {}
|
||||||
|
|
||||||
private _addError(node: ml.Node, message: string): void {
|
private _addError(node: ml.Node, message: string): void {
|
||||||
this._errors.push(new I18nError(node.sourceSpan, message));
|
this._errors.push(new I18nError(node.sourceSpan !, message));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -26,7 +26,7 @@ export class TranslationBundle {
|
|||||||
missingTranslationStrategy: MissingTranslationStrategy = MissingTranslationStrategy.Warning,
|
missingTranslationStrategy: MissingTranslationStrategy = MissingTranslationStrategy.Warning,
|
||||||
console?: Console) {
|
console?: Console) {
|
||||||
this._i18nToHtml = new I18nToHtmlVisitor(
|
this._i18nToHtml = new I18nToHtmlVisitor(
|
||||||
_i18nNodesByMsgId, locale, digest, mapperFactory, missingTranslationStrategy, console);
|
_i18nNodesByMsgId, locale, digest, mapperFactory !, missingTranslationStrategy, console);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Creates a `TranslationBundle` by parsing the given `content` with the `serializer`.
|
// Creates a `TranslationBundle` by parsing the given `content` with the `serializer`.
|
||||||
@ -36,7 +36,7 @@ export class TranslationBundle {
|
|||||||
console?: Console): TranslationBundle {
|
console?: Console): TranslationBundle {
|
||||||
const {locale, i18nNodesByMsgId} = serializer.load(content, url);
|
const {locale, i18nNodesByMsgId} = serializer.load(content, url);
|
||||||
const digestFn = (m: i18n.Message) => serializer.digest(m);
|
const digestFn = (m: i18n.Message) => serializer.digest(m);
|
||||||
const mapperFactory = (m: i18n.Message) => serializer.createNameMapper(m);
|
const mapperFactory = (m: i18n.Message) => serializer.createNameMapper(m) !;
|
||||||
return new TranslationBundle(
|
return new TranslationBundle(
|
||||||
i18nNodesByMsgId, locale, digestFn, mapperFactory, missingTranslationStrategy, console);
|
i18nNodesByMsgId, locale, digestFn, mapperFactory, missingTranslationStrategy, console);
|
||||||
}
|
}
|
||||||
@ -156,7 +156,7 @@ class I18nToHtmlVisitor implements i18n.Visitor {
|
|||||||
// When there is a translation use its nodes as the source
|
// When there is a translation use its nodes as the source
|
||||||
// And create a mapper to convert serialized placeholder names to internal names
|
// And create a mapper to convert serialized placeholder names to internal names
|
||||||
nodes = this._i18nNodesByMsgId[id];
|
nodes = this._i18nNodesByMsgId[id];
|
||||||
this._mapper = (name: string) => mapper ? mapper.toInternalName(name) : name;
|
this._mapper = (name: string) => mapper ? mapper.toInternalName(name) ! : name;
|
||||||
} else {
|
} else {
|
||||||
// When no translation has been found
|
// When no translation has been found
|
||||||
// - report an error / a warning / nothing,
|
// - report an error / a warning / nothing,
|
||||||
@ -175,7 +175,7 @@ class I18nToHtmlVisitor implements i18n.Visitor {
|
|||||||
this._mapper = (name: string) => name;
|
this._mapper = (name: string) => name;
|
||||||
}
|
}
|
||||||
const text = nodes.map(node => node.visit(this)).join('');
|
const text = nodes.map(node => node.visit(this)).join('');
|
||||||
const context = this._contextStack.pop();
|
const context = this._contextStack.pop() !;
|
||||||
this._srcMsg = context.msg;
|
this._srcMsg = context.msg;
|
||||||
this._mapper = context.mapper;
|
this._mapper = context.mapper;
|
||||||
return text;
|
return text;
|
||||||
|
@ -112,7 +112,7 @@ export class Identifiers {
|
|||||||
static createComponentFactory: IdentifierSpec = {name: 'ɵccf', moduleUrl: CORE, runtime: ɵccf};
|
static createComponentFactory: IdentifierSpec = {name: 'ɵccf', moduleUrl: CORE, runtime: ɵccf};
|
||||||
}
|
}
|
||||||
|
|
||||||
export function assetUrl(pkg: string, path: string = null, type: string = 'src'): string {
|
export function assetUrl(pkg: string, path: string | null = null, type: string = 'src'): string {
|
||||||
if (path == null) {
|
if (path == null) {
|
||||||
return `@angular/${pkg}`;
|
return `@angular/${pkg}`;
|
||||||
} else {
|
} else {
|
||||||
|
@ -49,20 +49,20 @@ export class JitCompiler implements Compiler {
|
|||||||
get injector(): Injector { return this._injector; }
|
get injector(): Injector { return this._injector; }
|
||||||
|
|
||||||
compileModuleSync<T>(moduleType: Type<T>): NgModuleFactory<T> {
|
compileModuleSync<T>(moduleType: Type<T>): NgModuleFactory<T> {
|
||||||
return this._compileModuleAndComponents(moduleType, true).syncResult;
|
return this._compileModuleAndComponents(moduleType, true).syncResult !;
|
||||||
}
|
}
|
||||||
|
|
||||||
compileModuleAsync<T>(moduleType: Type<T>): Promise<NgModuleFactory<T>> {
|
compileModuleAsync<T>(moduleType: Type<T>): Promise<NgModuleFactory<T>> {
|
||||||
return this._compileModuleAndComponents(moduleType, false).asyncResult;
|
return this._compileModuleAndComponents(moduleType, false).asyncResult !;
|
||||||
}
|
}
|
||||||
|
|
||||||
compileModuleAndAllComponentsSync<T>(moduleType: Type<T>): ModuleWithComponentFactories<T> {
|
compileModuleAndAllComponentsSync<T>(moduleType: Type<T>): ModuleWithComponentFactories<T> {
|
||||||
return this._compileModuleAndAllComponents(moduleType, true).syncResult;
|
return this._compileModuleAndAllComponents(moduleType, true).syncResult !;
|
||||||
}
|
}
|
||||||
|
|
||||||
compileModuleAndAllComponentsAsync<T>(moduleType: Type<T>):
|
compileModuleAndAllComponentsAsync<T>(moduleType: Type<T>):
|
||||||
Promise<ModuleWithComponentFactories<T>> {
|
Promise<ModuleWithComponentFactories<T>> {
|
||||||
return this._compileModuleAndAllComponents(moduleType, false).asyncResult;
|
return this._compileModuleAndAllComponents(moduleType, false).asyncResult !;
|
||||||
}
|
}
|
||||||
|
|
||||||
getNgContentSelectors(component: Type<any>): string[] {
|
getNgContentSelectors(component: Type<any>): string[] {
|
||||||
@ -72,7 +72,7 @@ export class JitCompiler implements Compiler {
|
|||||||
if (!template) {
|
if (!template) {
|
||||||
throw new Error(`The component ${stringify(component)} is not yet compiled!`);
|
throw new Error(`The component ${stringify(component)} is not yet compiled!`);
|
||||||
}
|
}
|
||||||
return template.compMeta.template.ngContentSelectors;
|
return template.compMeta.template !.ngContentSelectors;
|
||||||
}
|
}
|
||||||
|
|
||||||
private _compileModuleAndComponents<T>(moduleType: Type<T>, isSync: boolean):
|
private _compileModuleAndComponents<T>(moduleType: Type<T>, isSync: boolean):
|
||||||
@ -106,7 +106,7 @@ export class JitCompiler implements Compiler {
|
|||||||
|
|
||||||
private _loadModules(mainModule: any, isSync: boolean): Promise<any> {
|
private _loadModules(mainModule: any, isSync: boolean): Promise<any> {
|
||||||
const loadingPromises: Promise<any>[] = [];
|
const loadingPromises: Promise<any>[] = [];
|
||||||
const ngModule = this._metadataResolver.getNgModuleMetadata(mainModule);
|
const ngModule = this._metadataResolver.getNgModuleMetadata(mainModule) !;
|
||||||
// Note: the loadingPromise for a module only includes the loading of the exported directives
|
// Note: the loadingPromise for a module only includes the loading of the exported directives
|
||||||
// of imported modules.
|
// of imported modules.
|
||||||
// However, for runtime compilation, we want to transitively compile all modules,
|
// However, for runtime compilation, we want to transitively compile all modules,
|
||||||
@ -119,9 +119,9 @@ export class JitCompiler implements Compiler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private _compileModule<T>(moduleType: Type<T>): NgModuleFactory<T> {
|
private _compileModule<T>(moduleType: Type<T>): NgModuleFactory<T> {
|
||||||
let ngModuleFactory = this._compiledNgModuleCache.get(moduleType);
|
let ngModuleFactory = this._compiledNgModuleCache.get(moduleType) !;
|
||||||
if (!ngModuleFactory) {
|
if (!ngModuleFactory) {
|
||||||
const moduleMeta = this._metadataResolver.getNgModuleMetadata(moduleType);
|
const moduleMeta = this._metadataResolver.getNgModuleMetadata(moduleType) !;
|
||||||
// Always provide a bound Compiler
|
// Always provide a bound Compiler
|
||||||
const extraProviders = [this._metadataResolver.getProviderMetadata(new ProviderMeta(
|
const extraProviders = [this._metadataResolver.getProviderMetadata(new ProviderMeta(
|
||||||
Compiler, {useFactory: () => new ModuleBoundCompiler(this, moduleMeta.type.reference)}))];
|
Compiler, {useFactory: () => new ModuleBoundCompiler(this, moduleMeta.type.reference)}))];
|
||||||
@ -142,14 +142,14 @@ export class JitCompiler implements Compiler {
|
|||||||
/**
|
/**
|
||||||
* @internal
|
* @internal
|
||||||
*/
|
*/
|
||||||
_compileComponents(mainModule: Type<any>, allComponentFactories: ComponentFactory<any>[]) {
|
_compileComponents(mainModule: Type<any>, allComponentFactories: ComponentFactory<any>[]|null) {
|
||||||
const ngModule = this._metadataResolver.getNgModuleMetadata(mainModule);
|
const ngModule = this._metadataResolver.getNgModuleMetadata(mainModule) !;
|
||||||
const moduleByDirective = new Map<any, CompileNgModuleMetadata>();
|
const moduleByDirective = new Map<any, CompileNgModuleMetadata>();
|
||||||
const templates = new Set<CompiledTemplate>();
|
const templates = new Set<CompiledTemplate>();
|
||||||
|
|
||||||
ngModule.transitiveModule.modules.forEach((localModuleSummary) => {
|
ngModule.transitiveModule.modules.forEach((localModuleSummary) => {
|
||||||
const localModuleMeta =
|
const localModuleMeta =
|
||||||
this._metadataResolver.getNgModuleMetadata(localModuleSummary.reference);
|
this._metadataResolver.getNgModuleMetadata(localModuleSummary.reference) !;
|
||||||
localModuleMeta.declaredDirectives.forEach((dirIdentifier) => {
|
localModuleMeta.declaredDirectives.forEach((dirIdentifier) => {
|
||||||
moduleByDirective.set(dirIdentifier.reference, localModuleMeta);
|
moduleByDirective.set(dirIdentifier.reference, localModuleMeta);
|
||||||
const dirMeta = this._metadataResolver.getDirectiveMetadata(dirIdentifier.reference);
|
const dirMeta = this._metadataResolver.getDirectiveMetadata(dirIdentifier.reference);
|
||||||
@ -166,19 +166,19 @@ export class JitCompiler implements Compiler {
|
|||||||
});
|
});
|
||||||
ngModule.transitiveModule.modules.forEach((localModuleSummary) => {
|
ngModule.transitiveModule.modules.forEach((localModuleSummary) => {
|
||||||
const localModuleMeta =
|
const localModuleMeta =
|
||||||
this._metadataResolver.getNgModuleMetadata(localModuleSummary.reference);
|
this._metadataResolver.getNgModuleMetadata(localModuleSummary.reference) !;
|
||||||
localModuleMeta.declaredDirectives.forEach((dirIdentifier) => {
|
localModuleMeta.declaredDirectives.forEach((dirIdentifier) => {
|
||||||
const dirMeta = this._metadataResolver.getDirectiveMetadata(dirIdentifier.reference);
|
const dirMeta = this._metadataResolver.getDirectiveMetadata(dirIdentifier.reference);
|
||||||
if (dirMeta.isComponent) {
|
if (dirMeta.isComponent) {
|
||||||
dirMeta.entryComponents.forEach((entryComponentType) => {
|
dirMeta.entryComponents.forEach((entryComponentType) => {
|
||||||
const moduleMeta = moduleByDirective.get(entryComponentType.componentType);
|
const moduleMeta = moduleByDirective.get(entryComponentType.componentType) !;
|
||||||
templates.add(
|
templates.add(
|
||||||
this._createCompiledHostTemplate(entryComponentType.componentType, moduleMeta));
|
this._createCompiledHostTemplate(entryComponentType.componentType, moduleMeta));
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
localModuleMeta.entryComponents.forEach((entryComponentType) => {
|
localModuleMeta.entryComponents.forEach((entryComponentType) => {
|
||||||
const moduleMeta = moduleByDirective.get(entryComponentType.componentType);
|
const moduleMeta = moduleByDirective.get(entryComponentType.componentType) !;
|
||||||
templates.add(
|
templates.add(
|
||||||
this._createCompiledHostTemplate(entryComponentType.componentType, moduleMeta));
|
this._createCompiledHostTemplate(entryComponentType.componentType, moduleMeta));
|
||||||
});
|
});
|
||||||
@ -245,7 +245,7 @@ export class JitCompiler implements Compiler {
|
|||||||
const externalStylesheetsByModuleUrl = new Map<string, CompiledStylesheet>();
|
const externalStylesheetsByModuleUrl = new Map<string, CompiledStylesheet>();
|
||||||
const stylesCompileResult = this._styleCompiler.compileComponent(compMeta);
|
const stylesCompileResult = this._styleCompiler.compileComponent(compMeta);
|
||||||
stylesCompileResult.externalStylesheets.forEach(
|
stylesCompileResult.externalStylesheets.forEach(
|
||||||
(r) => { externalStylesheetsByModuleUrl.set(r.meta.moduleUrl, r); });
|
(r) => { externalStylesheetsByModuleUrl.set(r.meta.moduleUrl !, r); });
|
||||||
this._resolveStylesCompileResult(
|
this._resolveStylesCompileResult(
|
||||||
stylesCompileResult.componentStylesheet, externalStylesheetsByModuleUrl);
|
stylesCompileResult.componentStylesheet, externalStylesheetsByModuleUrl);
|
||||||
const directives =
|
const directives =
|
||||||
@ -253,8 +253,8 @@ export class JitCompiler implements Compiler {
|
|||||||
const pipes = template.ngModule.transitiveModule.pipes.map(
|
const pipes = template.ngModule.transitiveModule.pipes.map(
|
||||||
pipe => this._metadataResolver.getPipeSummary(pipe.reference));
|
pipe => this._metadataResolver.getPipeSummary(pipe.reference));
|
||||||
const {template: parsedTemplate, pipes: usedPipes} = this._templateParser.parse(
|
const {template: parsedTemplate, pipes: usedPipes} = this._templateParser.parse(
|
||||||
compMeta, compMeta.template.template, directives, pipes, template.ngModule.schemas,
|
compMeta, compMeta.template !.template !, directives, pipes, template.ngModule.schemas,
|
||||||
templateSourceUrl(template.ngModule.type, template.compMeta, template.compMeta.template));
|
templateSourceUrl(template.ngModule.type, template.compMeta, template.compMeta.template !));
|
||||||
const compileResult = this._viewCompiler.compileComponent(
|
const compileResult = this._viewCompiler.compileComponent(
|
||||||
compMeta, parsedTemplate, ir.variable(stylesCompileResult.componentStylesheet.stylesVar),
|
compMeta, parsedTemplate, ir.variable(stylesCompileResult.componentStylesheet.stylesVar),
|
||||||
usedPipes);
|
usedPipes);
|
||||||
@ -278,7 +278,7 @@ export class JitCompiler implements Compiler {
|
|||||||
private _resolveStylesCompileResult(
|
private _resolveStylesCompileResult(
|
||||||
result: CompiledStylesheet, externalStylesheetsByModuleUrl: Map<string, CompiledStylesheet>) {
|
result: CompiledStylesheet, externalStylesheetsByModuleUrl: Map<string, CompiledStylesheet>) {
|
||||||
result.dependencies.forEach((dep, i) => {
|
result.dependencies.forEach((dep, i) => {
|
||||||
const nestedCompileResult = externalStylesheetsByModuleUrl.get(dep.moduleUrl);
|
const nestedCompileResult = externalStylesheetsByModuleUrl.get(dep.moduleUrl) !;
|
||||||
const nestedStylesArr = this._resolveAndEvalStylesCompileResult(
|
const nestedStylesArr = this._resolveAndEvalStylesCompileResult(
|
||||||
nestedCompileResult, externalStylesheetsByModuleUrl);
|
nestedCompileResult, externalStylesheetsByModuleUrl);
|
||||||
dep.valuePlaceholder.reference = nestedStylesArr;
|
dep.valuePlaceholder.reference = nestedStylesArr;
|
||||||
@ -300,7 +300,7 @@ export class JitCompiler implements Compiler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class CompiledTemplate {
|
class CompiledTemplate {
|
||||||
private _viewClass: Function = null;
|
private _viewClass: Function = null !;
|
||||||
isCompiled = false;
|
isCompiled = false;
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
|
@ -59,7 +59,7 @@ export const COMPILER_PROVIDERS: Array<any|Type<any>|{[k: string]: any}|any[]> =
|
|||||||
useFactory: (parser: HtmlParser, translations: string, format: string, config: CompilerConfig,
|
useFactory: (parser: HtmlParser, translations: string, format: string, config: CompilerConfig,
|
||||||
console: Console) =>
|
console: Console) =>
|
||||||
new i18n.I18NHtmlParser(
|
new i18n.I18NHtmlParser(
|
||||||
parser, translations, format, config.missingTranslation, console),
|
parser, translations, format, config.missingTranslation !, console),
|
||||||
deps: [
|
deps: [
|
||||||
baseHtmlParser,
|
baseHtmlParser,
|
||||||
[new Optional(), new Inject(TRANSLATIONS)],
|
[new Optional(), new Inject(TRANSLATIONS)],
|
||||||
@ -123,7 +123,7 @@ export class JitCompilerFactory implements CompilerFactory {
|
|||||||
},
|
},
|
||||||
deps: []
|
deps: []
|
||||||
},
|
},
|
||||||
opts.providers
|
opts.providers !
|
||||||
]);
|
]);
|
||||||
return injector.get(Compiler);
|
return injector.get(Compiler);
|
||||||
}
|
}
|
||||||
@ -148,12 +148,12 @@ function _mergeOptions(optionsArr: CompilerOptions[]): CompilerOptions {
|
|||||||
return {
|
return {
|
||||||
useJit: _lastDefined(optionsArr.map(options => options.useJit)),
|
useJit: _lastDefined(optionsArr.map(options => options.useJit)),
|
||||||
defaultEncapsulation: _lastDefined(optionsArr.map(options => options.defaultEncapsulation)),
|
defaultEncapsulation: _lastDefined(optionsArr.map(options => options.defaultEncapsulation)),
|
||||||
providers: _mergeArrays(optionsArr.map(options => options.providers)),
|
providers: _mergeArrays(optionsArr.map(options => options.providers !)),
|
||||||
missingTranslation: _lastDefined(optionsArr.map(options => options.missingTranslation)),
|
missingTranslation: _lastDefined(optionsArr.map(options => options.missingTranslation)),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
function _lastDefined<T>(args: T[]): T {
|
function _lastDefined<T>(args: T[]): T|undefined {
|
||||||
for (let i = args.length - 1; i >= 0; i--) {
|
for (let i = args.length - 1; i >= 0; i--) {
|
||||||
if (args[i] !== undefined) {
|
if (args[i] !== undefined) {
|
||||||
return args[i];
|
return args[i];
|
||||||
|
@ -23,7 +23,7 @@ import {PipeResolver} from './pipe_resolver';
|
|||||||
import {ElementSchemaRegistry} from './schema/element_schema_registry';
|
import {ElementSchemaRegistry} from './schema/element_schema_registry';
|
||||||
import {SummaryResolver} from './summary_resolver';
|
import {SummaryResolver} from './summary_resolver';
|
||||||
import {getUrlScheme} from './url_resolver';
|
import {getUrlScheme} from './url_resolver';
|
||||||
import {MODULE_SUFFIX, ValueTransformer, syntaxError, visitValue} from './util';
|
import {MODULE_SUFFIX, ValueTransformer, noUndefined, syntaxError, visitValue} from './util';
|
||||||
|
|
||||||
export type ErrorCollector = (error: any, type?: any) => void;
|
export type ErrorCollector = (error: any, type?: any) => void;
|
||||||
export const ERROR_COLLECTOR_TOKEN = new InjectionToken('ErrorCollector');
|
export const ERROR_COLLECTOR_TOKEN = new InjectionToken('ErrorCollector');
|
||||||
@ -40,7 +40,7 @@ export class CompileMetadataResolver {
|
|||||||
private _nonNormalizedDirectiveCache =
|
private _nonNormalizedDirectiveCache =
|
||||||
new Map<Type<any>, {annotation: Directive, metadata: cpl.CompileDirectiveMetadata}>();
|
new Map<Type<any>, {annotation: Directive, metadata: cpl.CompileDirectiveMetadata}>();
|
||||||
private _directiveCache = new Map<Type<any>, cpl.CompileDirectiveMetadata>();
|
private _directiveCache = new Map<Type<any>, cpl.CompileDirectiveMetadata>();
|
||||||
private _summaryCache = new Map<Type<any>, cpl.CompileTypeSummary>();
|
private _summaryCache = new Map<Type<any>, cpl.CompileTypeSummary|null>();
|
||||||
private _pipeCache = new Map<Type<any>, cpl.CompilePipeMetadata>();
|
private _pipeCache = new Map<Type<any>, cpl.CompilePipeMetadata>();
|
||||||
private _ngModuleCache = new Map<Type<any>, cpl.CompileNgModuleMetadata>();
|
private _ngModuleCache = new Map<Type<any>, cpl.CompileNgModuleMetadata>();
|
||||||
private _ngModuleOfTypes = new Map<Type<any>, Type<any>>();
|
private _ngModuleOfTypes = new Map<Type<any>, Type<any>>();
|
||||||
@ -137,7 +137,7 @@ export class CompileMetadataResolver {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private getComponentFactory(
|
private getComponentFactory(
|
||||||
selector: string, dirType: any, inputs: {[key: string]: string},
|
selector: string, dirType: any, inputs: {[key: string]: string}|null,
|
||||||
outputs: {[key: string]: string}): StaticSymbol|ComponentFactory<any> {
|
outputs: {[key: string]: string}): StaticSymbol|ComponentFactory<any> {
|
||||||
if (dirType instanceof StaticSymbol) {
|
if (dirType instanceof StaticSymbol) {
|
||||||
return this._staticSymbolCache.get(
|
return this._staticSymbolCache.get(
|
||||||
@ -157,26 +157,27 @@ export class CompileMetadataResolver {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private _loadSummary(type: any, kind: cpl.CompileSummaryKind): cpl.CompileTypeSummary {
|
private _loadSummary(type: any, kind: cpl.CompileSummaryKind): cpl.CompileTypeSummary|null {
|
||||||
let typeSummary = this._summaryCache.get(type);
|
let typeSummary = this._summaryCache.get(type);
|
||||||
if (!typeSummary) {
|
if (!typeSummary) {
|
||||||
const summary = this._summaryResolver.resolveSummary(type);
|
const summary = this._summaryResolver.resolveSummary(type);
|
||||||
typeSummary = summary ? summary.type : null;
|
typeSummary = summary ? summary.type : null;
|
||||||
this._summaryCache.set(type, typeSummary);
|
this._summaryCache.set(type, typeSummary || null);
|
||||||
}
|
}
|
||||||
return typeSummary && typeSummary.summaryKind === kind ? typeSummary : null;
|
return typeSummary && typeSummary.summaryKind === kind ? typeSummary : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
private _loadDirectiveMetadata(ngModuleType: any, directiveType: any, isSync: boolean):
|
private _loadDirectiveMetadata(ngModuleType: any, directiveType: any, isSync: boolean):
|
||||||
Promise<any> {
|
Promise<any>|null {
|
||||||
if (this._directiveCache.has(directiveType)) {
|
if (this._directiveCache.has(directiveType)) {
|
||||||
return;
|
return null;
|
||||||
}
|
}
|
||||||
directiveType = resolveForwardRef(directiveType);
|
directiveType = resolveForwardRef(directiveType);
|
||||||
const {annotation, metadata} = this.getNonNormalizedDirectiveMetadata(directiveType);
|
const {annotation, metadata} = this.getNonNormalizedDirectiveMetadata(directiveType) !;
|
||||||
|
|
||||||
const createDirectiveMetadata = (templateMetadata: cpl.CompileTemplateMetadata) => {
|
const createDirectiveMetadata = (templateMetadata: cpl.CompileTemplateMetadata | null) => {
|
||||||
const normalizedDirMeta = new cpl.CompileDirectiveMetadata({
|
const normalizedDirMeta = new cpl.CompileDirectiveMetadata({
|
||||||
|
isHost: false,
|
||||||
type: metadata.type,
|
type: metadata.type,
|
||||||
isComponent: metadata.isComponent,
|
isComponent: metadata.isComponent,
|
||||||
selector: metadata.selector,
|
selector: metadata.selector,
|
||||||
@ -198,7 +199,7 @@ export class CompileMetadataResolver {
|
|||||||
template: templateMetadata
|
template: templateMetadata
|
||||||
});
|
});
|
||||||
if (templateMetadata) {
|
if (templateMetadata) {
|
||||||
this.initComponentFactory(metadata.componentFactory, templateMetadata.ngContentSelectors);
|
this.initComponentFactory(metadata.componentFactory !, templateMetadata.ngContentSelectors);
|
||||||
}
|
}
|
||||||
this._directiveCache.set(directiveType, normalizedDirMeta);
|
this._directiveCache.set(directiveType, normalizedDirMeta);
|
||||||
this._summaryCache.set(directiveType, normalizedDirMeta.toSummary());
|
this._summaryCache.set(directiveType, normalizedDirMeta.toSummary());
|
||||||
@ -206,17 +207,18 @@ export class CompileMetadataResolver {
|
|||||||
};
|
};
|
||||||
|
|
||||||
if (metadata.isComponent) {
|
if (metadata.isComponent) {
|
||||||
|
const template = metadata.template !;
|
||||||
const templateMeta = this._directiveNormalizer.normalizeTemplate({
|
const templateMeta = this._directiveNormalizer.normalizeTemplate({
|
||||||
ngModuleType,
|
ngModuleType,
|
||||||
componentType: directiveType,
|
componentType: directiveType,
|
||||||
moduleUrl: componentModuleUrl(this._reflector, directiveType, annotation),
|
moduleUrl: componentModuleUrl(this._reflector, directiveType, annotation),
|
||||||
encapsulation: metadata.template.encapsulation,
|
encapsulation: template.encapsulation,
|
||||||
template: metadata.template.template,
|
template: template.template,
|
||||||
templateUrl: metadata.template.templateUrl,
|
templateUrl: template.templateUrl,
|
||||||
styles: metadata.template.styles,
|
styles: template.styles,
|
||||||
styleUrls: metadata.template.styleUrls,
|
styleUrls: template.styleUrls,
|
||||||
animations: metadata.template.animations,
|
animations: template.animations,
|
||||||
interpolation: metadata.template.interpolation
|
interpolation: template.interpolation
|
||||||
});
|
});
|
||||||
if (templateMeta.syncResult) {
|
if (templateMeta.syncResult) {
|
||||||
createDirectiveMetadata(templateMeta.syncResult);
|
createDirectiveMetadata(templateMeta.syncResult);
|
||||||
@ -226,7 +228,7 @@ export class CompileMetadataResolver {
|
|||||||
this._reportError(componentStillLoadingError(directiveType), directiveType);
|
this._reportError(componentStillLoadingError(directiveType), directiveType);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
return templateMeta.asyncResult.then(createDirectiveMetadata);
|
return templateMeta.asyncResult !.then(createDirectiveMetadata);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// directive
|
// directive
|
||||||
@ -236,7 +238,7 @@ export class CompileMetadataResolver {
|
|||||||
}
|
}
|
||||||
|
|
||||||
getNonNormalizedDirectiveMetadata(directiveType: any):
|
getNonNormalizedDirectiveMetadata(directiveType: any):
|
||||||
{annotation: Directive, metadata: cpl.CompileDirectiveMetadata} {
|
{annotation: Directive, metadata: cpl.CompileDirectiveMetadata}|null {
|
||||||
directiveType = resolveForwardRef(directiveType);
|
directiveType = resolveForwardRef(directiveType);
|
||||||
if (!directiveType) {
|
if (!directiveType) {
|
||||||
return null;
|
return null;
|
||||||
@ -249,7 +251,7 @@ export class CompileMetadataResolver {
|
|||||||
if (!dirMeta) {
|
if (!dirMeta) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
let nonNormalizedTemplateMetadata: cpl.CompileTemplateMetadata;
|
let nonNormalizedTemplateMetadata: cpl.CompileTemplateMetadata = undefined !;
|
||||||
|
|
||||||
if (dirMeta instanceof Component) {
|
if (dirMeta instanceof Component) {
|
||||||
// component
|
// component
|
||||||
@ -260,25 +262,27 @@ export class CompileMetadataResolver {
|
|||||||
const animations = dirMeta.animations;
|
const animations = dirMeta.animations;
|
||||||
|
|
||||||
nonNormalizedTemplateMetadata = new cpl.CompileTemplateMetadata({
|
nonNormalizedTemplateMetadata = new cpl.CompileTemplateMetadata({
|
||||||
encapsulation: dirMeta.encapsulation,
|
encapsulation: noUndefined(dirMeta.encapsulation),
|
||||||
template: dirMeta.template,
|
template: noUndefined(dirMeta.template),
|
||||||
templateUrl: dirMeta.templateUrl,
|
templateUrl: noUndefined(dirMeta.templateUrl),
|
||||||
styles: dirMeta.styles,
|
styles: dirMeta.styles || [],
|
||||||
styleUrls: dirMeta.styleUrls,
|
styleUrls: dirMeta.styleUrls || [],
|
||||||
animations: animations,
|
animations: animations || [],
|
||||||
interpolation: dirMeta.interpolation,
|
interpolation: noUndefined(dirMeta.interpolation),
|
||||||
isInline: !!dirMeta.template
|
isInline: !!dirMeta.template,
|
||||||
|
externalStylesheets: [],
|
||||||
|
ngContentSelectors: []
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
let changeDetectionStrategy: ChangeDetectionStrategy = null;
|
let changeDetectionStrategy: ChangeDetectionStrategy = null !;
|
||||||
let viewProviders: cpl.CompileProviderMetadata[] = [];
|
let viewProviders: cpl.CompileProviderMetadata[] = [];
|
||||||
let entryComponentMetadata: cpl.CompileEntryComponentMetadata[] = [];
|
let entryComponentMetadata: cpl.CompileEntryComponentMetadata[] = [];
|
||||||
let selector = dirMeta.selector;
|
let selector = dirMeta.selector;
|
||||||
|
|
||||||
if (dirMeta instanceof Component) {
|
if (dirMeta instanceof Component) {
|
||||||
// Component
|
// Component
|
||||||
changeDetectionStrategy = dirMeta.changeDetection;
|
changeDetectionStrategy = dirMeta.changeDetection !;
|
||||||
if (dirMeta.viewProviders) {
|
if (dirMeta.viewProviders) {
|
||||||
viewProviders = this._getProvidersMetadata(
|
viewProviders = this._getProvidersMetadata(
|
||||||
dirMeta.viewProviders, entryComponentMetadata,
|
dirMeta.viewProviders, entryComponentMetadata,
|
||||||
@ -286,7 +290,7 @@ export class CompileMetadataResolver {
|
|||||||
}
|
}
|
||||||
if (dirMeta.entryComponents) {
|
if (dirMeta.entryComponents) {
|
||||||
entryComponentMetadata = flattenAndDedupeArray(dirMeta.entryComponents)
|
entryComponentMetadata = flattenAndDedupeArray(dirMeta.entryComponents)
|
||||||
.map((type) => this._getEntryComponentMetadata(type))
|
.map((type) => this._getEntryComponentMetadata(type) !)
|
||||||
.concat(entryComponentMetadata);
|
.concat(entryComponentMetadata);
|
||||||
}
|
}
|
||||||
if (!selector) {
|
if (!selector) {
|
||||||
@ -317,24 +321,25 @@ export class CompileMetadataResolver {
|
|||||||
}
|
}
|
||||||
|
|
||||||
const metadata = cpl.CompileDirectiveMetadata.create({
|
const metadata = cpl.CompileDirectiveMetadata.create({
|
||||||
|
isHost: false,
|
||||||
selector: selector,
|
selector: selector,
|
||||||
exportAs: dirMeta.exportAs,
|
exportAs: noUndefined(dirMeta.exportAs),
|
||||||
isComponent: !!nonNormalizedTemplateMetadata,
|
isComponent: !!nonNormalizedTemplateMetadata,
|
||||||
type: this._getTypeMetadata(directiveType),
|
type: this._getTypeMetadata(directiveType),
|
||||||
template: nonNormalizedTemplateMetadata,
|
template: nonNormalizedTemplateMetadata,
|
||||||
changeDetection: changeDetectionStrategy,
|
changeDetection: changeDetectionStrategy,
|
||||||
inputs: dirMeta.inputs,
|
inputs: dirMeta.inputs || [],
|
||||||
outputs: dirMeta.outputs,
|
outputs: dirMeta.outputs || [],
|
||||||
host: dirMeta.host,
|
host: dirMeta.host || {},
|
||||||
providers: providers,
|
providers: providers || [],
|
||||||
viewProviders: viewProviders,
|
viewProviders: viewProviders || [],
|
||||||
queries: queries,
|
queries: queries || [],
|
||||||
viewQueries: viewQueries,
|
viewQueries: viewQueries || [],
|
||||||
entryComponents: entryComponentMetadata,
|
entryComponents: entryComponentMetadata,
|
||||||
componentViewType: nonNormalizedTemplateMetadata ? this.getComponentViewClass(directiveType) :
|
componentViewType: nonNormalizedTemplateMetadata ? this.getComponentViewClass(directiveType) :
|
||||||
undefined,
|
null,
|
||||||
rendererType: nonNormalizedTemplateMetadata ? this.getRendererType(directiveType) : undefined,
|
rendererType: nonNormalizedTemplateMetadata ? this.getRendererType(directiveType) : null,
|
||||||
componentFactory: undefined
|
componentFactory: null
|
||||||
});
|
});
|
||||||
if (nonNormalizedTemplateMetadata) {
|
if (nonNormalizedTemplateMetadata) {
|
||||||
metadata.componentFactory =
|
metadata.componentFactory =
|
||||||
@ -350,7 +355,7 @@ export class CompileMetadataResolver {
|
|||||||
* This assumes `loadNgModuleDirectiveAndPipeMetadata` has been called first.
|
* This assumes `loadNgModuleDirectiveAndPipeMetadata` has been called first.
|
||||||
*/
|
*/
|
||||||
getDirectiveMetadata(directiveType: any): cpl.CompileDirectiveMetadata {
|
getDirectiveMetadata(directiveType: any): cpl.CompileDirectiveMetadata {
|
||||||
const dirMeta = this._directiveCache.get(directiveType);
|
const dirMeta = this._directiveCache.get(directiveType) !;
|
||||||
if (!dirMeta) {
|
if (!dirMeta) {
|
||||||
this._reportError(
|
this._reportError(
|
||||||
syntaxError(
|
syntaxError(
|
||||||
@ -376,8 +381,8 @@ export class CompileMetadataResolver {
|
|||||||
|
|
||||||
isPipe(type: any) { return this._pipeResolver.isPipe(type); }
|
isPipe(type: any) { return this._pipeResolver.isPipe(type); }
|
||||||
|
|
||||||
getNgModuleSummary(moduleType: any): cpl.CompileNgModuleSummary {
|
getNgModuleSummary(moduleType: any): cpl.CompileNgModuleSummary|null {
|
||||||
let moduleSummary =
|
let moduleSummary: cpl.CompileNgModuleSummary|null =
|
||||||
<cpl.CompileNgModuleSummary>this._loadSummary(moduleType, cpl.CompileSummaryKind.NgModule);
|
<cpl.CompileNgModuleSummary>this._loadSummary(moduleType, cpl.CompileSummaryKind.NgModule);
|
||||||
if (!moduleSummary) {
|
if (!moduleSummary) {
|
||||||
const moduleMeta = this.getNgModuleMetadata(moduleType, false);
|
const moduleMeta = this.getNgModuleMetadata(moduleType, false);
|
||||||
@ -408,7 +413,7 @@ export class CompileMetadataResolver {
|
|||||||
return Promise.all(loading);
|
return Promise.all(loading);
|
||||||
}
|
}
|
||||||
|
|
||||||
getNgModuleMetadata(moduleType: any, throwIfNotFound = true): cpl.CompileNgModuleMetadata {
|
getNgModuleMetadata(moduleType: any, throwIfNotFound = true): cpl.CompileNgModuleMetadata|null {
|
||||||
moduleType = resolveForwardRef(moduleType);
|
moduleType = resolveForwardRef(moduleType);
|
||||||
let compileMeta = this._ngModuleCache.get(moduleType);
|
let compileMeta = this._ngModuleCache.get(moduleType);
|
||||||
if (compileMeta) {
|
if (compileMeta) {
|
||||||
@ -430,7 +435,7 @@ export class CompileMetadataResolver {
|
|||||||
|
|
||||||
if (meta.imports) {
|
if (meta.imports) {
|
||||||
flattenAndDedupeArray(meta.imports).forEach((importedType) => {
|
flattenAndDedupeArray(meta.imports).forEach((importedType) => {
|
||||||
let importedModuleType: Type<any>;
|
let importedModuleType: Type<any> = undefined !;
|
||||||
if (isValidType(importedType)) {
|
if (isValidType(importedType)) {
|
||||||
importedModuleType = importedType;
|
importedModuleType = importedType;
|
||||||
} else if (importedType && importedType.ngModule) {
|
} else if (importedType && importedType.ngModule) {
|
||||||
@ -543,7 +548,7 @@ export class CompileMetadataResolver {
|
|||||||
|
|
||||||
if (meta.entryComponents) {
|
if (meta.entryComponents) {
|
||||||
entryComponents.push(...flattenAndDedupeArray(meta.entryComponents)
|
entryComponents.push(...flattenAndDedupeArray(meta.entryComponents)
|
||||||
.map(type => this._getEntryComponentMetadata(type)));
|
.map(type => this._getEntryComponentMetadata(type) !));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (meta.bootstrap) {
|
if (meta.bootstrap) {
|
||||||
@ -560,7 +565,7 @@ export class CompileMetadataResolver {
|
|||||||
}
|
}
|
||||||
|
|
||||||
entryComponents.push(
|
entryComponents.push(
|
||||||
...bootstrapComponents.map(type => this._getEntryComponentMetadata(type.reference)));
|
...bootstrapComponents.map(type => this._getEntryComponentMetadata(type.reference) !));
|
||||||
|
|
||||||
if (meta.schemas) {
|
if (meta.schemas) {
|
||||||
schemas.push(...flattenAndDedupeArray(meta.schemas));
|
schemas.push(...flattenAndDedupeArray(meta.schemas));
|
||||||
@ -579,11 +584,11 @@ export class CompileMetadataResolver {
|
|||||||
importedModules,
|
importedModules,
|
||||||
exportedModules,
|
exportedModules,
|
||||||
transitiveModule,
|
transitiveModule,
|
||||||
id: meta.id,
|
id: meta.id || null,
|
||||||
});
|
});
|
||||||
|
|
||||||
entryComponents.forEach((id) => transitiveModule.addEntryComponent(id));
|
entryComponents.forEach((id) => transitiveModule.addEntryComponent(id));
|
||||||
providers.forEach((provider) => transitiveModule.addProvider(provider, compileMeta.type));
|
providers.forEach((provider) => transitiveModule.addProvider(provider, compileMeta !.type));
|
||||||
transitiveModule.addModule(compileMeta.type);
|
transitiveModule.addModule(compileMeta.type);
|
||||||
this._ngModuleCache.set(moduleType, compileMeta);
|
this._ngModuleCache.set(moduleType, compileMeta);
|
||||||
return compileMeta;
|
return compileMeta;
|
||||||
@ -690,7 +695,7 @@ export class CompileMetadataResolver {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
private _getInjectableMetadata(type: Type<any>, dependencies: any[] = null):
|
private _getInjectableMetadata(type: Type<any>, dependencies: any[]|null = null):
|
||||||
cpl.CompileTypeMetadata {
|
cpl.CompileTypeMetadata {
|
||||||
const typeSummary = this._loadSummary(type, cpl.CompileSummaryKind.Injectable);
|
const typeSummary = this._loadSummary(type, cpl.CompileSummaryKind.Injectable);
|
||||||
if (typeSummary) {
|
if (typeSummary) {
|
||||||
@ -699,8 +704,9 @@ export class CompileMetadataResolver {
|
|||||||
return this._getTypeMetadata(type, dependencies);
|
return this._getTypeMetadata(type, dependencies);
|
||||||
}
|
}
|
||||||
|
|
||||||
private _getTypeMetadata(type: Type<any>, dependencies: any[] = null, throwOnUnknownDeps = true):
|
private _getTypeMetadata(
|
||||||
cpl.CompileTypeMetadata {
|
type: Type<any>, dependencies: any[]|null = null,
|
||||||
|
throwOnUnknownDeps = true): cpl.CompileTypeMetadata {
|
||||||
const identifier = this._getIdentifierMetadata(type);
|
const identifier = this._getIdentifierMetadata(type);
|
||||||
return {
|
return {
|
||||||
reference: identifier.reference,
|
reference: identifier.reference,
|
||||||
@ -710,7 +716,7 @@ export class CompileMetadataResolver {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
private _getFactoryMetadata(factory: Function, dependencies: any[] = null):
|
private _getFactoryMetadata(factory: Function, dependencies: any[]|null = null):
|
||||||
cpl.CompileFactoryMetadata {
|
cpl.CompileFactoryMetadata {
|
||||||
factory = resolveForwardRef(factory);
|
factory = resolveForwardRef(factory);
|
||||||
return {reference: factory, diDeps: this._getDependenciesMetadata(factory, dependencies)};
|
return {reference: factory, diDeps: this._getDependenciesMetadata(factory, dependencies)};
|
||||||
@ -720,7 +726,7 @@ export class CompileMetadataResolver {
|
|||||||
* Gets the metadata for the given pipe.
|
* Gets the metadata for the given pipe.
|
||||||
* This assumes `loadNgModuleDirectiveAndPipeMetadata` has been called first.
|
* This assumes `loadNgModuleDirectiveAndPipeMetadata` has been called first.
|
||||||
*/
|
*/
|
||||||
getPipeMetadata(pipeType: any): cpl.CompilePipeMetadata {
|
getPipeMetadata(pipeType: any): cpl.CompilePipeMetadata|null {
|
||||||
const pipeMeta = this._pipeCache.get(pipeType);
|
const pipeMeta = this._pipeCache.get(pipeType);
|
||||||
if (!pipeMeta) {
|
if (!pipeMeta) {
|
||||||
this._reportError(
|
this._reportError(
|
||||||
@ -728,7 +734,7 @@ export class CompileMetadataResolver {
|
|||||||
`Illegal state: getPipeMetadata can only be called after loadNgModuleDirectiveAndPipeMetadata for a module that declares it. Pipe ${stringifyType(pipeType)}.`),
|
`Illegal state: getPipeMetadata can only be called after loadNgModuleDirectiveAndPipeMetadata for a module that declares it. Pipe ${stringifyType(pipeType)}.`),
|
||||||
pipeType);
|
pipeType);
|
||||||
}
|
}
|
||||||
return pipeMeta;
|
return pipeMeta || null;
|
||||||
}
|
}
|
||||||
|
|
||||||
getPipeSummary(pipeType: any): cpl.CompilePipeSummary {
|
getPipeSummary(pipeType: any): cpl.CompilePipeSummary {
|
||||||
@ -753,12 +759,12 @@ export class CompileMetadataResolver {
|
|||||||
|
|
||||||
private _loadPipeMetadata(pipeType: any): cpl.CompilePipeMetadata {
|
private _loadPipeMetadata(pipeType: any): cpl.CompilePipeMetadata {
|
||||||
pipeType = resolveForwardRef(pipeType);
|
pipeType = resolveForwardRef(pipeType);
|
||||||
const pipeAnnotation = this._pipeResolver.resolve(pipeType);
|
const pipeAnnotation = this._pipeResolver.resolve(pipeType) !;
|
||||||
|
|
||||||
const pipeMeta = new cpl.CompilePipeMetadata({
|
const pipeMeta = new cpl.CompilePipeMetadata({
|
||||||
type: this._getTypeMetadata(pipeType),
|
type: this._getTypeMetadata(pipeType),
|
||||||
name: pipeAnnotation.name,
|
name: pipeAnnotation.name,
|
||||||
pure: pipeAnnotation.pure
|
pure: !!pipeAnnotation.pure
|
||||||
});
|
});
|
||||||
this._pipeCache.set(pipeType, pipeMeta);
|
this._pipeCache.set(pipeType, pipeMeta);
|
||||||
this._summaryCache.set(pipeType, pipeMeta.toSummary());
|
this._summaryCache.set(pipeType, pipeMeta.toSummary());
|
||||||
@ -766,7 +772,7 @@ export class CompileMetadataResolver {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private _getDependenciesMetadata(
|
private _getDependenciesMetadata(
|
||||||
typeOrFunc: Type<any>|Function, dependencies: any[],
|
typeOrFunc: Type<any>|Function, dependencies: any[]|null,
|
||||||
throwOnUnknownDeps = true): cpl.CompileDiDependencyMetadata[] {
|
throwOnUnknownDeps = true): cpl.CompileDiDependencyMetadata[] {
|
||||||
let hasUnknownDeps = false;
|
let hasUnknownDeps = false;
|
||||||
const params = dependencies || this._reflector.parameters(typeOrFunc) || [];
|
const params = dependencies || this._reflector.parameters(typeOrFunc) || [];
|
||||||
@ -804,7 +810,7 @@ export class CompileMetadataResolver {
|
|||||||
}
|
}
|
||||||
if (token == null) {
|
if (token == null) {
|
||||||
hasUnknownDeps = true;
|
hasUnknownDeps = true;
|
||||||
return null;
|
return null !;
|
||||||
}
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
@ -853,7 +859,7 @@ export class CompileMetadataResolver {
|
|||||||
this._getProvidersMetadata(provider, targetEntryComponents, debugInfo, compileProviders);
|
this._getProvidersMetadata(provider, targetEntryComponents, debugInfo, compileProviders);
|
||||||
} else {
|
} else {
|
||||||
provider = resolveForwardRef(provider);
|
provider = resolveForwardRef(provider);
|
||||||
let providerMeta: cpl.ProviderMeta;
|
let providerMeta: cpl.ProviderMeta = undefined !;
|
||||||
if (provider && typeof provider === 'object' && provider.hasOwnProperty('provide')) {
|
if (provider && typeof provider === 'object' && provider.hasOwnProperty('provide')) {
|
||||||
this._validateProvider(provider);
|
this._validateProvider(provider);
|
||||||
providerMeta = new cpl.ProviderMeta(provider.provide, provider);
|
providerMeta = new cpl.ProviderMeta(provider.provide, provider);
|
||||||
@ -933,25 +939,26 @@ export class CompileMetadataResolver {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private _getEntryComponentMetadata(dirType: any, throwIfNotFound = true):
|
private _getEntryComponentMetadata(dirType: any, throwIfNotFound = true):
|
||||||
cpl.CompileEntryComponentMetadata {
|
cpl.CompileEntryComponentMetadata|null {
|
||||||
const dirMeta = this.getNonNormalizedDirectiveMetadata(dirType);
|
const dirMeta = this.getNonNormalizedDirectiveMetadata(dirType);
|
||||||
if (dirMeta && dirMeta.metadata.isComponent) {
|
if (dirMeta && dirMeta.metadata.isComponent) {
|
||||||
return {componentType: dirType, componentFactory: dirMeta.metadata.componentFactory};
|
return {componentType: dirType, componentFactory: dirMeta.metadata.componentFactory !};
|
||||||
}
|
}
|
||||||
const dirSummary =
|
const dirSummary =
|
||||||
<cpl.CompileDirectiveSummary>this._loadSummary(dirType, cpl.CompileSummaryKind.Directive);
|
<cpl.CompileDirectiveSummary>this._loadSummary(dirType, cpl.CompileSummaryKind.Directive);
|
||||||
if (dirSummary && dirSummary.isComponent) {
|
if (dirSummary && dirSummary.isComponent) {
|
||||||
return {componentType: dirType, componentFactory: dirSummary.componentFactory};
|
return {componentType: dirType, componentFactory: dirSummary.componentFactory !};
|
||||||
}
|
}
|
||||||
if (throwIfNotFound) {
|
if (throwIfNotFound) {
|
||||||
throw syntaxError(`${dirType.name} cannot be used as an entry component.`);
|
throw syntaxError(`${dirType.name} cannot be used as an entry component.`);
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
getProviderMetadata(provider: cpl.ProviderMeta): cpl.CompileProviderMetadata {
|
getProviderMetadata(provider: cpl.ProviderMeta): cpl.CompileProviderMetadata {
|
||||||
let compileDeps: cpl.CompileDiDependencyMetadata[];
|
let compileDeps: cpl.CompileDiDependencyMetadata[] = undefined !;
|
||||||
let compileTypeMetadata: cpl.CompileTypeMetadata = null;
|
let compileTypeMetadata: cpl.CompileTypeMetadata = null !;
|
||||||
let compileFactoryMetadata: cpl.CompileFactoryMetadata = null;
|
let compileFactoryMetadata: cpl.CompileFactoryMetadata = null !;
|
||||||
let token: cpl.CompileTokenMetadata = this._getTokenMetadata(provider.token);
|
let token: cpl.CompileTokenMetadata = this._getTokenMetadata(provider.token);
|
||||||
|
|
||||||
if (provider.useClass) {
|
if (provider.useClass) {
|
||||||
@ -971,7 +978,7 @@ export class CompileMetadataResolver {
|
|||||||
useClass: compileTypeMetadata,
|
useClass: compileTypeMetadata,
|
||||||
useValue: provider.useValue,
|
useValue: provider.useValue,
|
||||||
useFactory: compileFactoryMetadata,
|
useFactory: compileFactoryMetadata,
|
||||||
useExisting: provider.useExisting ? this._getTokenMetadata(provider.useExisting) : null,
|
useExisting: provider.useExisting ? this._getTokenMetadata(provider.useExisting) : undefined,
|
||||||
deps: compileDeps,
|
deps: compileDeps,
|
||||||
multi: provider.multi
|
multi: provider.multi
|
||||||
};
|
};
|
||||||
@ -1016,7 +1023,7 @@ export class CompileMetadataResolver {
|
|||||||
selectors,
|
selectors,
|
||||||
first: q.first,
|
first: q.first,
|
||||||
descendants: q.descendants, propertyName,
|
descendants: q.descendants, propertyName,
|
||||||
read: q.read ? this._getTokenMetadata(q.read) : null
|
read: q.read ? this._getTokenMetadata(q.read) : null !
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1078,7 +1085,7 @@ export function componentModuleUrl(
|
|||||||
`If you're using Webpack you should inline the template and the styles, see https://goo.gl/X2J8zc.`);
|
`If you're using Webpack you should inline the template and the styles, see https://goo.gl/X2J8zc.`);
|
||||||
}
|
}
|
||||||
|
|
||||||
return reflector.importUri(type);
|
return reflector.importUri(type) !;
|
||||||
}
|
}
|
||||||
|
|
||||||
function extractIdentifiers(value: any, targetIdentifiers: cpl.CompileIdentifierMetadata[]) {
|
function extractIdentifiers(value: any, targetIdentifiers: cpl.CompileIdentifierMetadata[]) {
|
||||||
|
@ -9,12 +9,12 @@
|
|||||||
import {ParseSourceSpan} from '../parse_util';
|
import {ParseSourceSpan} from '../parse_util';
|
||||||
|
|
||||||
export interface Node {
|
export interface Node {
|
||||||
sourceSpan: ParseSourceSpan;
|
sourceSpan: ParseSourceSpan|null;
|
||||||
visit(visitor: Visitor, context: any): any;
|
visit(visitor: Visitor, context: any): any;
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Text implements Node {
|
export class Text implements Node {
|
||||||
constructor(public value: string, public sourceSpan: ParseSourceSpan) {}
|
constructor(public value: string, public sourceSpan: ParseSourceSpan|null) {}
|
||||||
visit(visitor: Visitor, context: any): any { return visitor.visitText(this, context); }
|
visit(visitor: Visitor, context: any): any { return visitor.visitText(this, context); }
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -43,13 +43,14 @@ export class Attribute implements Node {
|
|||||||
export class Element implements Node {
|
export class Element implements Node {
|
||||||
constructor(
|
constructor(
|
||||||
public name: string, public attrs: Attribute[], public children: Node[],
|
public name: string, public attrs: Attribute[], public children: Node[],
|
||||||
public sourceSpan: ParseSourceSpan, public startSourceSpan: ParseSourceSpan,
|
public sourceSpan: ParseSourceSpan|null = null,
|
||||||
public endSourceSpan: ParseSourceSpan) {}
|
public startSourceSpan: ParseSourceSpan|null = null,
|
||||||
|
public endSourceSpan: ParseSourceSpan|null = null) {}
|
||||||
visit(visitor: Visitor, context: any): any { return visitor.visitElement(this, context); }
|
visit(visitor: Visitor, context: any): any { return visitor.visitElement(this, context); }
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Comment implements Node {
|
export class Comment implements Node {
|
||||||
constructor(public value: string, public sourceSpan: ParseSourceSpan) {}
|
constructor(public value: string|null, public sourceSpan: ParseSourceSpan) {}
|
||||||
visit(visitor: Visitor, context: any): any { return visitor.visitComment(this, context); }
|
visit(visitor: Visitor, context: any): any { return visitor.visitComment(this, context); }
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -70,7 +71,7 @@ export function visitAll(visitor: Visitor, nodes: Node[], context: any = null):
|
|||||||
const result: any[] = [];
|
const result: any[] = [];
|
||||||
|
|
||||||
const visit = visitor.visit ?
|
const visit = visitor.visit ?
|
||||||
(ast: Node) => visitor.visit(ast, context) || ast.visit(visitor, context) :
|
(ast: Node) => visitor.visit !(ast, context) || ast.visit(visitor, context) :
|
||||||
(ast: Node) => ast.visit(visitor, context);
|
(ast: Node) => ast.visit(visitor, context);
|
||||||
nodes.forEach(ast => {
|
nodes.forEach(ast => {
|
||||||
const astResult = visit(ast);
|
const astResult = visit(ast);
|
||||||
|
@ -14,7 +14,7 @@ export class HtmlTagDefinition implements TagDefinition {
|
|||||||
closedByParent: boolean = false;
|
closedByParent: boolean = false;
|
||||||
requiredParents: {[key: string]: boolean};
|
requiredParents: {[key: string]: boolean};
|
||||||
parentToAdd: string;
|
parentToAdd: string;
|
||||||
implicitNamespacePrefix: string;
|
implicitNamespacePrefix: string|null;
|
||||||
contentType: TagContentType;
|
contentType: TagContentType;
|
||||||
isVoid: boolean;
|
isVoid: boolean;
|
||||||
ignoreFirstLf: boolean;
|
ignoreFirstLf: boolean;
|
||||||
@ -43,7 +43,7 @@ export class HtmlTagDefinition implements TagDefinition {
|
|||||||
this.parentToAdd = requiredParents[0];
|
this.parentToAdd = requiredParents[0];
|
||||||
requiredParents.forEach(tagName => this.requiredParents[tagName] = true);
|
requiredParents.forEach(tagName => this.requiredParents[tagName] = true);
|
||||||
}
|
}
|
||||||
this.implicitNamespacePrefix = implicitNamespacePrefix;
|
this.implicitNamespacePrefix = implicitNamespacePrefix || null;
|
||||||
this.contentType = contentType;
|
this.contentType = contentType;
|
||||||
this.ignoreFirstLf = ignoreFirstLf;
|
this.ignoreFirstLf = ignoreFirstLf;
|
||||||
}
|
}
|
||||||
|
@ -9,7 +9,7 @@
|
|||||||
import {assertInterpolationSymbols} from '../assertions';
|
import {assertInterpolationSymbols} from '../assertions';
|
||||||
|
|
||||||
export class InterpolationConfig {
|
export class InterpolationConfig {
|
||||||
static fromArray(markers: [string, string]): InterpolationConfig {
|
static fromArray(markers: [string, string]|null): InterpolationConfig {
|
||||||
if (!markers) {
|
if (!markers) {
|
||||||
return DEFAULT_INTERPOLATION_CONFIG;
|
return DEFAULT_INTERPOLATION_CONFIG;
|
||||||
}
|
}
|
||||||
|
@ -198,8 +198,8 @@ class _Tokenizer {
|
|||||||
const token =
|
const token =
|
||||||
new Token(this._currentTokenType, parts, new ParseSourceSpan(this._currentTokenStart, end));
|
new Token(this._currentTokenType, parts, new ParseSourceSpan(this._currentTokenStart, end));
|
||||||
this.tokens.push(token);
|
this.tokens.push(token);
|
||||||
this._currentTokenStart = null;
|
this._currentTokenStart = null !;
|
||||||
this._currentTokenType = null;
|
this._currentTokenType = null !;
|
||||||
return token;
|
return token;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -208,8 +208,8 @@ class _Tokenizer {
|
|||||||
msg += ` (Do you have an unescaped "{" in your template? Use "{{ '{' }}") to escape it.)`;
|
msg += ` (Do you have an unescaped "{" in your template? Use "{{ '{' }}") to escape it.)`;
|
||||||
}
|
}
|
||||||
const error = new TokenError(msg, this._currentTokenType, span);
|
const error = new TokenError(msg, this._currentTokenType, span);
|
||||||
this._currentTokenStart = null;
|
this._currentTokenStart = null !;
|
||||||
this._currentTokenType = null;
|
this._currentTokenType = null !;
|
||||||
return new _ControlFlowError(error);
|
return new _ControlFlowError(error);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -402,7 +402,7 @@ class _Tokenizer {
|
|||||||
|
|
||||||
private _consumePrefixAndName(): string[] {
|
private _consumePrefixAndName(): string[] {
|
||||||
const nameOrPrefixStart = this._index;
|
const nameOrPrefixStart = this._index;
|
||||||
let prefix: string = null;
|
let prefix: string = null !;
|
||||||
while (this._peek !== chars.$COLON && !isPrefixEnd(this._peek)) {
|
while (this._peek !== chars.$COLON && !isPrefixEnd(this._peek)) {
|
||||||
this._advance();
|
this._advance();
|
||||||
}
|
}
|
||||||
@ -473,7 +473,7 @@ class _Tokenizer {
|
|||||||
return this._attemptCharCode(chars.$GT);
|
return this._attemptCharCode(chars.$GT);
|
||||||
});
|
});
|
||||||
this._beginToken(TokenType.TAG_CLOSE, textToken.sourceSpan.end);
|
this._beginToken(TokenType.TAG_CLOSE, textToken.sourceSpan.end);
|
||||||
this._endToken([null, lowercaseTagName]);
|
this._endToken([null !, lowercaseTagName]);
|
||||||
}
|
}
|
||||||
|
|
||||||
private _consumeTagOpenStart(start: ParseLocation) {
|
private _consumeTagOpenStart(start: ParseLocation) {
|
||||||
@ -697,7 +697,7 @@ function toUpperCaseCharCode(code: number): number {
|
|||||||
|
|
||||||
function mergeTextTokens(srcTokens: Token[]): Token[] {
|
function mergeTextTokens(srcTokens: Token[]): Token[] {
|
||||||
const dstTokens: Token[] = [];
|
const dstTokens: Token[] = [];
|
||||||
let lastDstToken: Token;
|
let lastDstToken: Token|undefined = undefined;
|
||||||
for (let i = 0; i < srcTokens.length; i++) {
|
for (let i = 0; i < srcTokens.length; i++) {
|
||||||
const token = srcTokens[i];
|
const token = srcTokens[i];
|
||||||
if (lastDstToken && lastDstToken.type == TokenType.TEXT && token.type == TokenType.TEXT) {
|
if (lastDstToken && lastDstToken.type == TokenType.TEXT && token.type == TokenType.TEXT) {
|
||||||
|
@ -14,11 +14,13 @@ import * as lex from './lexer';
|
|||||||
import {TagDefinition, getNsPrefix, mergeNsAndName} from './tags';
|
import {TagDefinition, getNsPrefix, mergeNsAndName} from './tags';
|
||||||
|
|
||||||
export class TreeError extends ParseError {
|
export class TreeError extends ParseError {
|
||||||
static create(elementName: string, span: ParseSourceSpan, msg: string): TreeError {
|
static create(elementName: string|null, span: ParseSourceSpan, msg: string): TreeError {
|
||||||
return new TreeError(elementName, span, msg);
|
return new TreeError(elementName, span, msg);
|
||||||
}
|
}
|
||||||
|
|
||||||
constructor(public elementName: string, span: ParseSourceSpan, msg: string) { super(span, msg); }
|
constructor(public elementName: string|null, span: ParseSourceSpan, msg: string) {
|
||||||
|
super(span, msg);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class ParseTreeResult {
|
export class ParseTreeResult {
|
||||||
@ -93,7 +95,7 @@ class _TreeBuilder {
|
|||||||
return prev;
|
return prev;
|
||||||
}
|
}
|
||||||
|
|
||||||
private _advanceIf(type: lex.TokenType): lex.Token {
|
private _advanceIf(type: lex.TokenType): lex.Token|null {
|
||||||
if (this._peek.type === type) {
|
if (this._peek.type === type) {
|
||||||
return this._advance();
|
return this._advance();
|
||||||
}
|
}
|
||||||
@ -138,7 +140,7 @@ class _TreeBuilder {
|
|||||||
this._advance();
|
this._advance();
|
||||||
}
|
}
|
||||||
|
|
||||||
private _parseExpansionCase(): html.ExpansionCase {
|
private _parseExpansionCase(): html.ExpansionCase|null {
|
||||||
const value = this._advance();
|
const value = this._advance();
|
||||||
|
|
||||||
// read {
|
// read {
|
||||||
@ -170,7 +172,7 @@ class _TreeBuilder {
|
|||||||
value.parts[0], parsedExp.rootNodes, sourceSpan, value.sourceSpan, expSourceSpan);
|
value.parts[0], parsedExp.rootNodes, sourceSpan, value.sourceSpan, expSourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
private _collectExpansionExpTokens(start: lex.Token): lex.Token[] {
|
private _collectExpansionExpTokens(start: lex.Token): lex.Token[]|null {
|
||||||
const exp: lex.Token[] = [];
|
const exp: lex.Token[] = [];
|
||||||
const expansionFormStack = [lex.TokenType.EXPANSION_CASE_EXP_START];
|
const expansionFormStack = [lex.TokenType.EXPANSION_CASE_EXP_START];
|
||||||
|
|
||||||
@ -263,7 +265,7 @@ class _TreeBuilder {
|
|||||||
}
|
}
|
||||||
const end = this._peek.sourceSpan.start;
|
const end = this._peek.sourceSpan.start;
|
||||||
const span = new ParseSourceSpan(startTagToken.sourceSpan.start, end);
|
const span = new ParseSourceSpan(startTagToken.sourceSpan.start, end);
|
||||||
const el = new html.Element(fullName, attrs, [], span, span, null);
|
const el = new html.Element(fullName, attrs, [], span, span, undefined);
|
||||||
this._pushElement(el);
|
this._pushElement(el);
|
||||||
if (selfClosing) {
|
if (selfClosing) {
|
||||||
this._popElement(fullName);
|
this._popElement(fullName);
|
||||||
@ -297,7 +299,7 @@ class _TreeBuilder {
|
|||||||
endTagToken.parts[0], endTagToken.parts[1], this._getParentElement());
|
endTagToken.parts[0], endTagToken.parts[1], this._getParentElement());
|
||||||
|
|
||||||
if (this._getParentElement()) {
|
if (this._getParentElement()) {
|
||||||
this._getParentElement().endSourceSpan = endTagToken.sourceSpan;
|
this._getParentElement() !.endSourceSpan = endTagToken.sourceSpan;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (this.getTagDefinition(fullName).isVoid) {
|
if (this.getTagDefinition(fullName).isVoid) {
|
||||||
@ -330,7 +332,7 @@ class _TreeBuilder {
|
|||||||
const fullName = mergeNsAndName(attrName.parts[0], attrName.parts[1]);
|
const fullName = mergeNsAndName(attrName.parts[0], attrName.parts[1]);
|
||||||
let end = attrName.sourceSpan.end;
|
let end = attrName.sourceSpan.end;
|
||||||
let value = '';
|
let value = '';
|
||||||
let valueSpan: ParseSourceSpan;
|
let valueSpan: ParseSourceSpan = undefined !;
|
||||||
if (this._peek.type === lex.TokenType.ATTR_VALUE) {
|
if (this._peek.type === lex.TokenType.ATTR_VALUE) {
|
||||||
const valueToken = this._advance();
|
const valueToken = this._advance();
|
||||||
value = valueToken.parts[0];
|
value = valueToken.parts[0];
|
||||||
@ -341,7 +343,7 @@ class _TreeBuilder {
|
|||||||
fullName, value, new ParseSourceSpan(attrName.sourceSpan.start, end), valueSpan);
|
fullName, value, new ParseSourceSpan(attrName.sourceSpan.start, end), valueSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
private _getParentElement(): html.Element {
|
private _getParentElement(): html.Element|null {
|
||||||
return this._elementStack.length > 0 ? this._elementStack[this._elementStack.length - 1] : null;
|
return this._elementStack.length > 0 ? this._elementStack[this._elementStack.length - 1] : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -351,7 +353,7 @@ class _TreeBuilder {
|
|||||||
* `<ng-container>` elements are skipped as they are not rendered as DOM element.
|
* `<ng-container>` elements are skipped as they are not rendered as DOM element.
|
||||||
*/
|
*/
|
||||||
private _getParentElementSkippingContainers(): {parent: html.Element, container: html.Element} {
|
private _getParentElementSkippingContainers(): {parent: html.Element, container: html.Element} {
|
||||||
let container: html.Element = null;
|
let container: html.Element = null !;
|
||||||
|
|
||||||
for (let i = this._elementStack.length - 1; i >= 0; i--) {
|
for (let i = this._elementStack.length - 1; i >= 0; i--) {
|
||||||
if (this._elementStack[i].name !== 'ng-container') {
|
if (this._elementStack[i].name !== 'ng-container') {
|
||||||
@ -397,10 +399,10 @@ class _TreeBuilder {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private _getElementFullName(prefix: string, localName: string, parentElement: html.Element):
|
private _getElementFullName(prefix: string, localName: string, parentElement: html.Element|null):
|
||||||
string {
|
string {
|
||||||
if (prefix == null) {
|
if (prefix == null) {
|
||||||
prefix = this.getTagDefinition(localName).implicitNamespacePrefix;
|
prefix = this.getTagDefinition(localName).implicitNamespacePrefix !;
|
||||||
if (prefix == null && parentElement != null) {
|
if (prefix == null && parentElement != null) {
|
||||||
prefix = getNsPrefix(parentElement.name);
|
prefix = getNsPrefix(parentElement.name);
|
||||||
}
|
}
|
||||||
|
@ -17,7 +17,7 @@ export interface TagDefinition {
|
|||||||
closedByParent: boolean;
|
closedByParent: boolean;
|
||||||
requiredParents: {[key: string]: boolean};
|
requiredParents: {[key: string]: boolean};
|
||||||
parentToAdd: string;
|
parentToAdd: string;
|
||||||
implicitNamespacePrefix: string;
|
implicitNamespacePrefix: string|null;
|
||||||
contentType: TagContentType;
|
contentType: TagContentType;
|
||||||
isVoid: boolean;
|
isVoid: boolean;
|
||||||
ignoreFirstLf: boolean;
|
ignoreFirstLf: boolean;
|
||||||
@ -28,7 +28,7 @@ export interface TagDefinition {
|
|||||||
isClosedByChild(name: string): boolean;
|
isClosedByChild(name: string): boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function splitNsName(elementName: string): [string, string] {
|
export function splitNsName(elementName: string): [string | null, string] {
|
||||||
if (elementName[0] != ':') {
|
if (elementName[0] != ':') {
|
||||||
return [null, elementName];
|
return [null, elementName];
|
||||||
}
|
}
|
||||||
@ -42,269 +42,274 @@ export function splitNsName(elementName: string): [string, string] {
|
|||||||
return [elementName.slice(1, colonIndex), elementName.slice(colonIndex + 1)];
|
return [elementName.slice(1, colonIndex), elementName.slice(colonIndex + 1)];
|
||||||
}
|
}
|
||||||
|
|
||||||
export function getNsPrefix(fullName: string): string {
|
export function getNsPrefix(fullName: string): string
|
||||||
return fullName === null ? null : splitNsName(fullName)[0];
|
export function getNsPrefix(fullName: null): null;
|
||||||
}
|
export function getNsPrefix(fullName: string | null): string |
|
||||||
|
null {
|
||||||
|
return fullName === null ? null : splitNsName(fullName)[0];
|
||||||
|
}
|
||||||
|
|
||||||
export function mergeNsAndName(prefix: string, localName: string): string {
|
export function mergeNsAndName(prefix: string, localName: string):
|
||||||
return prefix ? `:${prefix}:${localName}` : localName;
|
string {
|
||||||
}
|
return prefix ? `:${prefix}:${localName}` : localName;
|
||||||
|
}
|
||||||
|
|
||||||
// see http://www.w3.org/TR/html51/syntax.html#named-character-references
|
// see http://www.w3.org/TR/html51/syntax.html#named-character-references
|
||||||
// see https://html.spec.whatwg.org/multipage/entities.json
|
// see https://html.spec.whatwg.org/multipage/entities.json
|
||||||
// This list is not exhaustive to keep the compiler footprint low.
|
// This list is not exhaustive to keep the compiler footprint low.
|
||||||
// The `{` / `ƫ` syntax should be used when the named character reference does not exist.
|
// The `{` / `ƫ` syntax should be used when the named character reference does not
|
||||||
export const NAMED_ENTITIES: {[k: string]: string} = {
|
// exist.
|
||||||
'Aacute': '\u00C1',
|
export const NAMED_ENTITIES: {[k: string]: string} = {
|
||||||
'aacute': '\u00E1',
|
'Aacute': '\u00C1',
|
||||||
'Acirc': '\u00C2',
|
'aacute': '\u00E1',
|
||||||
'acirc': '\u00E2',
|
'Acirc': '\u00C2',
|
||||||
'acute': '\u00B4',
|
'acirc': '\u00E2',
|
||||||
'AElig': '\u00C6',
|
'acute': '\u00B4',
|
||||||
'aelig': '\u00E6',
|
'AElig': '\u00C6',
|
||||||
'Agrave': '\u00C0',
|
'aelig': '\u00E6',
|
||||||
'agrave': '\u00E0',
|
'Agrave': '\u00C0',
|
||||||
'alefsym': '\u2135',
|
'agrave': '\u00E0',
|
||||||
'Alpha': '\u0391',
|
'alefsym': '\u2135',
|
||||||
'alpha': '\u03B1',
|
'Alpha': '\u0391',
|
||||||
'amp': '&',
|
'alpha': '\u03B1',
|
||||||
'and': '\u2227',
|
'amp': '&',
|
||||||
'ang': '\u2220',
|
'and': '\u2227',
|
||||||
'apos': '\u0027',
|
'ang': '\u2220',
|
||||||
'Aring': '\u00C5',
|
'apos': '\u0027',
|
||||||
'aring': '\u00E5',
|
'Aring': '\u00C5',
|
||||||
'asymp': '\u2248',
|
'aring': '\u00E5',
|
||||||
'Atilde': '\u00C3',
|
'asymp': '\u2248',
|
||||||
'atilde': '\u00E3',
|
'Atilde': '\u00C3',
|
||||||
'Auml': '\u00C4',
|
'atilde': '\u00E3',
|
||||||
'auml': '\u00E4',
|
'Auml': '\u00C4',
|
||||||
'bdquo': '\u201E',
|
'auml': '\u00E4',
|
||||||
'Beta': '\u0392',
|
'bdquo': '\u201E',
|
||||||
'beta': '\u03B2',
|
'Beta': '\u0392',
|
||||||
'brvbar': '\u00A6',
|
'beta': '\u03B2',
|
||||||
'bull': '\u2022',
|
'brvbar': '\u00A6',
|
||||||
'cap': '\u2229',
|
'bull': '\u2022',
|
||||||
'Ccedil': '\u00C7',
|
'cap': '\u2229',
|
||||||
'ccedil': '\u00E7',
|
'Ccedil': '\u00C7',
|
||||||
'cedil': '\u00B8',
|
'ccedil': '\u00E7',
|
||||||
'cent': '\u00A2',
|
'cedil': '\u00B8',
|
||||||
'Chi': '\u03A7',
|
'cent': '\u00A2',
|
||||||
'chi': '\u03C7',
|
'Chi': '\u03A7',
|
||||||
'circ': '\u02C6',
|
'chi': '\u03C7',
|
||||||
'clubs': '\u2663',
|
'circ': '\u02C6',
|
||||||
'cong': '\u2245',
|
'clubs': '\u2663',
|
||||||
'copy': '\u00A9',
|
'cong': '\u2245',
|
||||||
'crarr': '\u21B5',
|
'copy': '\u00A9',
|
||||||
'cup': '\u222A',
|
'crarr': '\u21B5',
|
||||||
'curren': '\u00A4',
|
'cup': '\u222A',
|
||||||
'dagger': '\u2020',
|
'curren': '\u00A4',
|
||||||
'Dagger': '\u2021',
|
'dagger': '\u2020',
|
||||||
'darr': '\u2193',
|
'Dagger': '\u2021',
|
||||||
'dArr': '\u21D3',
|
'darr': '\u2193',
|
||||||
'deg': '\u00B0',
|
'dArr': '\u21D3',
|
||||||
'Delta': '\u0394',
|
'deg': '\u00B0',
|
||||||
'delta': '\u03B4',
|
'Delta': '\u0394',
|
||||||
'diams': '\u2666',
|
'delta': '\u03B4',
|
||||||
'divide': '\u00F7',
|
'diams': '\u2666',
|
||||||
'Eacute': '\u00C9',
|
'divide': '\u00F7',
|
||||||
'eacute': '\u00E9',
|
'Eacute': '\u00C9',
|
||||||
'Ecirc': '\u00CA',
|
'eacute': '\u00E9',
|
||||||
'ecirc': '\u00EA',
|
'Ecirc': '\u00CA',
|
||||||
'Egrave': '\u00C8',
|
'ecirc': '\u00EA',
|
||||||
'egrave': '\u00E8',
|
'Egrave': '\u00C8',
|
||||||
'empty': '\u2205',
|
'egrave': '\u00E8',
|
||||||
'emsp': '\u2003',
|
'empty': '\u2205',
|
||||||
'ensp': '\u2002',
|
'emsp': '\u2003',
|
||||||
'Epsilon': '\u0395',
|
'ensp': '\u2002',
|
||||||
'epsilon': '\u03B5',
|
'Epsilon': '\u0395',
|
||||||
'equiv': '\u2261',
|
'epsilon': '\u03B5',
|
||||||
'Eta': '\u0397',
|
'equiv': '\u2261',
|
||||||
'eta': '\u03B7',
|
'Eta': '\u0397',
|
||||||
'ETH': '\u00D0',
|
'eta': '\u03B7',
|
||||||
'eth': '\u00F0',
|
'ETH': '\u00D0',
|
||||||
'Euml': '\u00CB',
|
'eth': '\u00F0',
|
||||||
'euml': '\u00EB',
|
'Euml': '\u00CB',
|
||||||
'euro': '\u20AC',
|
'euml': '\u00EB',
|
||||||
'exist': '\u2203',
|
'euro': '\u20AC',
|
||||||
'fnof': '\u0192',
|
'exist': '\u2203',
|
||||||
'forall': '\u2200',
|
'fnof': '\u0192',
|
||||||
'frac12': '\u00BD',
|
'forall': '\u2200',
|
||||||
'frac14': '\u00BC',
|
'frac12': '\u00BD',
|
||||||
'frac34': '\u00BE',
|
'frac14': '\u00BC',
|
||||||
'frasl': '\u2044',
|
'frac34': '\u00BE',
|
||||||
'Gamma': '\u0393',
|
'frasl': '\u2044',
|
||||||
'gamma': '\u03B3',
|
'Gamma': '\u0393',
|
||||||
'ge': '\u2265',
|
'gamma': '\u03B3',
|
||||||
'gt': '>',
|
'ge': '\u2265',
|
||||||
'harr': '\u2194',
|
'gt': '>',
|
||||||
'hArr': '\u21D4',
|
'harr': '\u2194',
|
||||||
'hearts': '\u2665',
|
'hArr': '\u21D4',
|
||||||
'hellip': '\u2026',
|
'hearts': '\u2665',
|
||||||
'Iacute': '\u00CD',
|
'hellip': '\u2026',
|
||||||
'iacute': '\u00ED',
|
'Iacute': '\u00CD',
|
||||||
'Icirc': '\u00CE',
|
'iacute': '\u00ED',
|
||||||
'icirc': '\u00EE',
|
'Icirc': '\u00CE',
|
||||||
'iexcl': '\u00A1',
|
'icirc': '\u00EE',
|
||||||
'Igrave': '\u00CC',
|
'iexcl': '\u00A1',
|
||||||
'igrave': '\u00EC',
|
'Igrave': '\u00CC',
|
||||||
'image': '\u2111',
|
'igrave': '\u00EC',
|
||||||
'infin': '\u221E',
|
'image': '\u2111',
|
||||||
'int': '\u222B',
|
'infin': '\u221E',
|
||||||
'Iota': '\u0399',
|
'int': '\u222B',
|
||||||
'iota': '\u03B9',
|
'Iota': '\u0399',
|
||||||
'iquest': '\u00BF',
|
'iota': '\u03B9',
|
||||||
'isin': '\u2208',
|
'iquest': '\u00BF',
|
||||||
'Iuml': '\u00CF',
|
'isin': '\u2208',
|
||||||
'iuml': '\u00EF',
|
'Iuml': '\u00CF',
|
||||||
'Kappa': '\u039A',
|
'iuml': '\u00EF',
|
||||||
'kappa': '\u03BA',
|
'Kappa': '\u039A',
|
||||||
'Lambda': '\u039B',
|
'kappa': '\u03BA',
|
||||||
'lambda': '\u03BB',
|
'Lambda': '\u039B',
|
||||||
'lang': '\u27E8',
|
'lambda': '\u03BB',
|
||||||
'laquo': '\u00AB',
|
'lang': '\u27E8',
|
||||||
'larr': '\u2190',
|
'laquo': '\u00AB',
|
||||||
'lArr': '\u21D0',
|
'larr': '\u2190',
|
||||||
'lceil': '\u2308',
|
'lArr': '\u21D0',
|
||||||
'ldquo': '\u201C',
|
'lceil': '\u2308',
|
||||||
'le': '\u2264',
|
'ldquo': '\u201C',
|
||||||
'lfloor': '\u230A',
|
'le': '\u2264',
|
||||||
'lowast': '\u2217',
|
'lfloor': '\u230A',
|
||||||
'loz': '\u25CA',
|
'lowast': '\u2217',
|
||||||
'lrm': '\u200E',
|
'loz': '\u25CA',
|
||||||
'lsaquo': '\u2039',
|
'lrm': '\u200E',
|
||||||
'lsquo': '\u2018',
|
'lsaquo': '\u2039',
|
||||||
'lt': '<',
|
'lsquo': '\u2018',
|
||||||
'macr': '\u00AF',
|
'lt': '<',
|
||||||
'mdash': '\u2014',
|
'macr': '\u00AF',
|
||||||
'micro': '\u00B5',
|
'mdash': '\u2014',
|
||||||
'middot': '\u00B7',
|
'micro': '\u00B5',
|
||||||
'minus': '\u2212',
|
'middot': '\u00B7',
|
||||||
'Mu': '\u039C',
|
'minus': '\u2212',
|
||||||
'mu': '\u03BC',
|
'Mu': '\u039C',
|
||||||
'nabla': '\u2207',
|
'mu': '\u03BC',
|
||||||
'nbsp': '\u00A0',
|
'nabla': '\u2207',
|
||||||
'ndash': '\u2013',
|
'nbsp': '\u00A0',
|
||||||
'ne': '\u2260',
|
'ndash': '\u2013',
|
||||||
'ni': '\u220B',
|
'ne': '\u2260',
|
||||||
'not': '\u00AC',
|
'ni': '\u220B',
|
||||||
'notin': '\u2209',
|
'not': '\u00AC',
|
||||||
'nsub': '\u2284',
|
'notin': '\u2209',
|
||||||
'Ntilde': '\u00D1',
|
'nsub': '\u2284',
|
||||||
'ntilde': '\u00F1',
|
'Ntilde': '\u00D1',
|
||||||
'Nu': '\u039D',
|
'ntilde': '\u00F1',
|
||||||
'nu': '\u03BD',
|
'Nu': '\u039D',
|
||||||
'Oacute': '\u00D3',
|
'nu': '\u03BD',
|
||||||
'oacute': '\u00F3',
|
'Oacute': '\u00D3',
|
||||||
'Ocirc': '\u00D4',
|
'oacute': '\u00F3',
|
||||||
'ocirc': '\u00F4',
|
'Ocirc': '\u00D4',
|
||||||
'OElig': '\u0152',
|
'ocirc': '\u00F4',
|
||||||
'oelig': '\u0153',
|
'OElig': '\u0152',
|
||||||
'Ograve': '\u00D2',
|
'oelig': '\u0153',
|
||||||
'ograve': '\u00F2',
|
'Ograve': '\u00D2',
|
||||||
'oline': '\u203E',
|
'ograve': '\u00F2',
|
||||||
'Omega': '\u03A9',
|
'oline': '\u203E',
|
||||||
'omega': '\u03C9',
|
'Omega': '\u03A9',
|
||||||
'Omicron': '\u039F',
|
'omega': '\u03C9',
|
||||||
'omicron': '\u03BF',
|
'Omicron': '\u039F',
|
||||||
'oplus': '\u2295',
|
'omicron': '\u03BF',
|
||||||
'or': '\u2228',
|
'oplus': '\u2295',
|
||||||
'ordf': '\u00AA',
|
'or': '\u2228',
|
||||||
'ordm': '\u00BA',
|
'ordf': '\u00AA',
|
||||||
'Oslash': '\u00D8',
|
'ordm': '\u00BA',
|
||||||
'oslash': '\u00F8',
|
'Oslash': '\u00D8',
|
||||||
'Otilde': '\u00D5',
|
'oslash': '\u00F8',
|
||||||
'otilde': '\u00F5',
|
'Otilde': '\u00D5',
|
||||||
'otimes': '\u2297',
|
'otilde': '\u00F5',
|
||||||
'Ouml': '\u00D6',
|
'otimes': '\u2297',
|
||||||
'ouml': '\u00F6',
|
'Ouml': '\u00D6',
|
||||||
'para': '\u00B6',
|
'ouml': '\u00F6',
|
||||||
'permil': '\u2030',
|
'para': '\u00B6',
|
||||||
'perp': '\u22A5',
|
'permil': '\u2030',
|
||||||
'Phi': '\u03A6',
|
'perp': '\u22A5',
|
||||||
'phi': '\u03C6',
|
'Phi': '\u03A6',
|
||||||
'Pi': '\u03A0',
|
'phi': '\u03C6',
|
||||||
'pi': '\u03C0',
|
'Pi': '\u03A0',
|
||||||
'piv': '\u03D6',
|
'pi': '\u03C0',
|
||||||
'plusmn': '\u00B1',
|
'piv': '\u03D6',
|
||||||
'pound': '\u00A3',
|
'plusmn': '\u00B1',
|
||||||
'prime': '\u2032',
|
'pound': '\u00A3',
|
||||||
'Prime': '\u2033',
|
'prime': '\u2032',
|
||||||
'prod': '\u220F',
|
'Prime': '\u2033',
|
||||||
'prop': '\u221D',
|
'prod': '\u220F',
|
||||||
'Psi': '\u03A8',
|
'prop': '\u221D',
|
||||||
'psi': '\u03C8',
|
'Psi': '\u03A8',
|
||||||
'quot': '\u0022',
|
'psi': '\u03C8',
|
||||||
'radic': '\u221A',
|
'quot': '\u0022',
|
||||||
'rang': '\u27E9',
|
'radic': '\u221A',
|
||||||
'raquo': '\u00BB',
|
'rang': '\u27E9',
|
||||||
'rarr': '\u2192',
|
'raquo': '\u00BB',
|
||||||
'rArr': '\u21D2',
|
'rarr': '\u2192',
|
||||||
'rceil': '\u2309',
|
'rArr': '\u21D2',
|
||||||
'rdquo': '\u201D',
|
'rceil': '\u2309',
|
||||||
'real': '\u211C',
|
'rdquo': '\u201D',
|
||||||
'reg': '\u00AE',
|
'real': '\u211C',
|
||||||
'rfloor': '\u230B',
|
'reg': '\u00AE',
|
||||||
'Rho': '\u03A1',
|
'rfloor': '\u230B',
|
||||||
'rho': '\u03C1',
|
'Rho': '\u03A1',
|
||||||
'rlm': '\u200F',
|
'rho': '\u03C1',
|
||||||
'rsaquo': '\u203A',
|
'rlm': '\u200F',
|
||||||
'rsquo': '\u2019',
|
'rsaquo': '\u203A',
|
||||||
'sbquo': '\u201A',
|
'rsquo': '\u2019',
|
||||||
'Scaron': '\u0160',
|
'sbquo': '\u201A',
|
||||||
'scaron': '\u0161',
|
'Scaron': '\u0160',
|
||||||
'sdot': '\u22C5',
|
'scaron': '\u0161',
|
||||||
'sect': '\u00A7',
|
'sdot': '\u22C5',
|
||||||
'shy': '\u00AD',
|
'sect': '\u00A7',
|
||||||
'Sigma': '\u03A3',
|
'shy': '\u00AD',
|
||||||
'sigma': '\u03C3',
|
'Sigma': '\u03A3',
|
||||||
'sigmaf': '\u03C2',
|
'sigma': '\u03C3',
|
||||||
'sim': '\u223C',
|
'sigmaf': '\u03C2',
|
||||||
'spades': '\u2660',
|
'sim': '\u223C',
|
||||||
'sub': '\u2282',
|
'spades': '\u2660',
|
||||||
'sube': '\u2286',
|
'sub': '\u2282',
|
||||||
'sum': '\u2211',
|
'sube': '\u2286',
|
||||||
'sup': '\u2283',
|
'sum': '\u2211',
|
||||||
'sup1': '\u00B9',
|
'sup': '\u2283',
|
||||||
'sup2': '\u00B2',
|
'sup1': '\u00B9',
|
||||||
'sup3': '\u00B3',
|
'sup2': '\u00B2',
|
||||||
'supe': '\u2287',
|
'sup3': '\u00B3',
|
||||||
'szlig': '\u00DF',
|
'supe': '\u2287',
|
||||||
'Tau': '\u03A4',
|
'szlig': '\u00DF',
|
||||||
'tau': '\u03C4',
|
'Tau': '\u03A4',
|
||||||
'there4': '\u2234',
|
'tau': '\u03C4',
|
||||||
'Theta': '\u0398',
|
'there4': '\u2234',
|
||||||
'theta': '\u03B8',
|
'Theta': '\u0398',
|
||||||
'thetasym': '\u03D1',
|
'theta': '\u03B8',
|
||||||
'thinsp': '\u2009',
|
'thetasym': '\u03D1',
|
||||||
'THORN': '\u00DE',
|
'thinsp': '\u2009',
|
||||||
'thorn': '\u00FE',
|
'THORN': '\u00DE',
|
||||||
'tilde': '\u02DC',
|
'thorn': '\u00FE',
|
||||||
'times': '\u00D7',
|
'tilde': '\u02DC',
|
||||||
'trade': '\u2122',
|
'times': '\u00D7',
|
||||||
'Uacute': '\u00DA',
|
'trade': '\u2122',
|
||||||
'uacute': '\u00FA',
|
'Uacute': '\u00DA',
|
||||||
'uarr': '\u2191',
|
'uacute': '\u00FA',
|
||||||
'uArr': '\u21D1',
|
'uarr': '\u2191',
|
||||||
'Ucirc': '\u00DB',
|
'uArr': '\u21D1',
|
||||||
'ucirc': '\u00FB',
|
'Ucirc': '\u00DB',
|
||||||
'Ugrave': '\u00D9',
|
'ucirc': '\u00FB',
|
||||||
'ugrave': '\u00F9',
|
'Ugrave': '\u00D9',
|
||||||
'uml': '\u00A8',
|
'ugrave': '\u00F9',
|
||||||
'upsih': '\u03D2',
|
'uml': '\u00A8',
|
||||||
'Upsilon': '\u03A5',
|
'upsih': '\u03D2',
|
||||||
'upsilon': '\u03C5',
|
'Upsilon': '\u03A5',
|
||||||
'Uuml': '\u00DC',
|
'upsilon': '\u03C5',
|
||||||
'uuml': '\u00FC',
|
'Uuml': '\u00DC',
|
||||||
'weierp': '\u2118',
|
'uuml': '\u00FC',
|
||||||
'Xi': '\u039E',
|
'weierp': '\u2118',
|
||||||
'xi': '\u03BE',
|
'Xi': '\u039E',
|
||||||
'Yacute': '\u00DD',
|
'xi': '\u03BE',
|
||||||
'yacute': '\u00FD',
|
'Yacute': '\u00DD',
|
||||||
'yen': '\u00A5',
|
'yacute': '\u00FD',
|
||||||
'yuml': '\u00FF',
|
'yen': '\u00A5',
|
||||||
'Yuml': '\u0178',
|
'yuml': '\u00FF',
|
||||||
'Zeta': '\u0396',
|
'Yuml': '\u0178',
|
||||||
'zeta': '\u03B6',
|
'Zeta': '\u0396',
|
||||||
'zwj': '\u200D',
|
'zeta': '\u03B6',
|
||||||
'zwnj': '\u200C',
|
'zwj': '\u200D',
|
||||||
};
|
'zwnj': '\u200C',
|
||||||
|
};
|
||||||
|
@ -15,6 +15,6 @@ export class XmlParser extends Parser {
|
|||||||
constructor() { super(getXmlTagDefinition); }
|
constructor() { super(getXmlTagDefinition); }
|
||||||
|
|
||||||
parse(source: string, url: string, parseExpansionForms: boolean = false): ParseTreeResult {
|
parse(source: string, url: string, parseExpansionForms: boolean = false): ParseTreeResult {
|
||||||
return super.parse(source, url, parseExpansionForms, null);
|
return super.parse(source, url, parseExpansionForms);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -63,7 +63,7 @@ export class NgModuleCompiler {
|
|||||||
[o.variable(injectorClass.name), o.importExpr(ngModuleMeta.type)],
|
[o.variable(injectorClass.name), o.importExpr(ngModuleMeta.type)],
|
||||||
o.importType(
|
o.importType(
|
||||||
createIdentifier(Identifiers.NgModuleFactory),
|
createIdentifier(Identifiers.NgModuleFactory),
|
||||||
[o.importType(ngModuleMeta.type)], [o.TypeModifier.Const])))
|
[o.importType(ngModuleMeta.type) !], [o.TypeModifier.Const])))
|
||||||
.toDeclStmt(null, [o.StmtModifier.Final]);
|
.toDeclStmt(null, [o.StmtModifier.Final]);
|
||||||
|
|
||||||
const stmts: o.Statement[] = [injectorClass, ngModuleFactoryStmt];
|
const stmts: o.Statement[] = [injectorClass, ngModuleFactoryStmt];
|
||||||
@ -106,7 +106,7 @@ class _InjectorBuilder implements ClassBuilder {
|
|||||||
if (resolvedProvider.lifecycleHooks.indexOf(ɵLifecycleHooks.OnDestroy) !== -1) {
|
if (resolvedProvider.lifecycleHooks.indexOf(ɵLifecycleHooks.OnDestroy) !== -1) {
|
||||||
let callNgOnDestroy: o.Expression = instance.callMethod('ngOnDestroy', []);
|
let callNgOnDestroy: o.Expression = instance.callMethod('ngOnDestroy', []);
|
||||||
if (!resolvedProvider.eager) {
|
if (!resolvedProvider.eager) {
|
||||||
callNgOnDestroy = this._lazyProps.get(instance.name).and(callNgOnDestroy);
|
callNgOnDestroy = this._lazyProps.get(instance.name) !.and(callNgOnDestroy);
|
||||||
}
|
}
|
||||||
this._destroyStmts.push(callNgOnDestroy.toStmt());
|
this._destroyStmts.push(callNgOnDestroy.toStmt());
|
||||||
}
|
}
|
||||||
@ -116,7 +116,7 @@ class _InjectorBuilder implements ClassBuilder {
|
|||||||
|
|
||||||
build(): o.ClassStmt {
|
build(): o.ClassStmt {
|
||||||
const getMethodStmts: o.Statement[] = this._tokens.map((token) => {
|
const getMethodStmts: o.Statement[] = this._tokens.map((token) => {
|
||||||
const providerExpr = this._instances.get(tokenReference(token));
|
const providerExpr = this._instances.get(tokenReference(token)) !;
|
||||||
return new o.IfStmt(
|
return new o.IfStmt(
|
||||||
InjectMethodVars.token.identical(createDiTokenExpression(token)),
|
InjectMethodVars.token.identical(createDiTokenExpression(token)),
|
||||||
[new o.ReturnStatement(providerExpr)]);
|
[new o.ReturnStatement(providerExpr)]);
|
||||||
@ -124,13 +124,13 @@ class _InjectorBuilder implements ClassBuilder {
|
|||||||
const methods = [
|
const methods = [
|
||||||
new o.ClassMethod(
|
new o.ClassMethod(
|
||||||
'createInternal', [], this._createStmts.concat(new o.ReturnStatement(
|
'createInternal', [], this._createStmts.concat(new o.ReturnStatement(
|
||||||
this._instances.get(this._ngModuleMeta.type.reference))),
|
this._instances.get(this._ngModuleMeta.type.reference) !)),
|
||||||
o.importType(this._ngModuleMeta.type)),
|
o.importType(this._ngModuleMeta.type)),
|
||||||
new o.ClassMethod(
|
new o.ClassMethod(
|
||||||
'getInternal',
|
'getInternal',
|
||||||
[
|
[
|
||||||
new o.FnParam(InjectMethodVars.token.name, o.DYNAMIC_TYPE),
|
new o.FnParam(InjectMethodVars.token.name !, o.DYNAMIC_TYPE),
|
||||||
new o.FnParam(InjectMethodVars.notFoundResult.name, o.DYNAMIC_TYPE)
|
new o.FnParam(InjectMethodVars.notFoundResult.name !, o.DYNAMIC_TYPE)
|
||||||
],
|
],
|
||||||
getMethodStmts.concat([new o.ReturnStatement(InjectMethodVars.notFoundResult)]),
|
getMethodStmts.concat([new o.ReturnStatement(InjectMethodVars.notFoundResult)]),
|
||||||
o.DYNAMIC_TYPE),
|
o.DYNAMIC_TYPE),
|
||||||
@ -150,7 +150,8 @@ class _InjectorBuilder implements ClassBuilder {
|
|||||||
ctorParams: [new o.FnParam(
|
ctorParams: [new o.FnParam(
|
||||||
InjectorProps.parent.name, o.importType(createIdentifier(Identifiers.Injector)))],
|
InjectorProps.parent.name, o.importType(createIdentifier(Identifiers.Injector)))],
|
||||||
parent: o.importExpr(
|
parent: o.importExpr(
|
||||||
createIdentifier(Identifiers.NgModuleInjector), [o.importType(this._ngModuleMeta.type)]),
|
createIdentifier(Identifiers.NgModuleInjector),
|
||||||
|
[o.importType(this._ngModuleMeta.type) !]),
|
||||||
parentArgs: parentArgs,
|
parentArgs: parentArgs,
|
||||||
builders: [{methods}, this]
|
builders: [{methods}, this]
|
||||||
});
|
});
|
||||||
@ -186,7 +187,7 @@ class _InjectorBuilder implements ClassBuilder {
|
|||||||
type = new o.ArrayType(o.DYNAMIC_TYPE);
|
type = new o.ArrayType(o.DYNAMIC_TYPE);
|
||||||
} else {
|
} else {
|
||||||
resolvedProviderValueExpr = providerValueExpressions[0];
|
resolvedProviderValueExpr = providerValueExpressions[0];
|
||||||
type = providerValueExpressions[0].type;
|
type = providerValueExpressions[0].type !;
|
||||||
}
|
}
|
||||||
if (!type) {
|
if (!type) {
|
||||||
type = o.DYNAMIC_TYPE;
|
type = o.DYNAMIC_TYPE;
|
||||||
@ -211,7 +212,7 @@ class _InjectorBuilder implements ClassBuilder {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private _getDependency(dep: CompileDiDependencyMetadata): o.Expression {
|
private _getDependency(dep: CompileDiDependencyMetadata): o.Expression {
|
||||||
let result: o.Expression = null;
|
let result: o.Expression = null !;
|
||||||
if (dep.isValue) {
|
if (dep.isValue) {
|
||||||
result = o.literal(dep.value);
|
result = o.literal(dep.value);
|
||||||
}
|
}
|
||||||
@ -226,11 +227,11 @@ class _InjectorBuilder implements ClassBuilder {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!result) {
|
if (!result) {
|
||||||
result = this._instances.get(tokenReference(dep.token));
|
result = this._instances.get(tokenReference(dep.token !)) !;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (!result) {
|
if (!result) {
|
||||||
const args = [createDiTokenExpression(dep.token)];
|
const args = [createDiTokenExpression(dep.token !)];
|
||||||
if (dep.isOptional) {
|
if (dep.isOptional) {
|
||||||
args.push(o.NULL_EXPR);
|
args.push(o.NULL_EXPR);
|
||||||
}
|
}
|
||||||
@ -244,7 +245,7 @@ function createDiTokenExpression(token: CompileTokenMetadata): o.Expression {
|
|||||||
if (token.value != null) {
|
if (token.value != null) {
|
||||||
return o.literal(token.value);
|
return o.literal(token.value);
|
||||||
} else {
|
} else {
|
||||||
return o.importExpr(token.identifier);
|
return o.importExpr(token.identifier !);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -23,7 +23,7 @@ export class NgModuleResolver {
|
|||||||
|
|
||||||
isNgModule(type: any) { return this._reflector.annotations(type).some(_isNgModuleMetadata); }
|
isNgModule(type: any) { return this._reflector.annotations(type).some(_isNgModuleMetadata); }
|
||||||
|
|
||||||
resolve(type: Type<any>, throwIfNotFound = true): NgModule {
|
resolve(type: Type<any>, throwIfNotFound = true): NgModule|null {
|
||||||
const ngModuleMeta: NgModule = findLast(this._reflector.annotations(type), _isNgModuleMetadata);
|
const ngModuleMeta: NgModule = findLast(this._reflector.annotations(type), _isNgModuleMetadata);
|
||||||
|
|
||||||
if (ngModuleMeta) {
|
if (ngModuleMeta) {
|
||||||
|
@ -14,18 +14,18 @@ import {SourceMapGenerator} from './source_map';
|
|||||||
const _SINGLE_QUOTE_ESCAPE_STRING_RE = /'|\\|\n|\r|\$/g;
|
const _SINGLE_QUOTE_ESCAPE_STRING_RE = /'|\\|\n|\r|\$/g;
|
||||||
const _LEGAL_IDENTIFIER_RE = /^[$A-Z_][0-9A-Z_$]*$/i;
|
const _LEGAL_IDENTIFIER_RE = /^[$A-Z_][0-9A-Z_$]*$/i;
|
||||||
const _INDENT_WITH = ' ';
|
const _INDENT_WITH = ' ';
|
||||||
export const CATCH_ERROR_VAR = o.variable('error');
|
export const CATCH_ERROR_VAR = o.variable('error', null, null);
|
||||||
export const CATCH_STACK_VAR = o.variable('stack');
|
export const CATCH_STACK_VAR = o.variable('stack', null, null);
|
||||||
|
|
||||||
export abstract class OutputEmitter {
|
export abstract class OutputEmitter {
|
||||||
abstract emitStatements(
|
abstract emitStatements(
|
||||||
srcFilePath: string, genFilePath: string, stmts: o.Statement[], exportedVars: string[],
|
srcFilePath: string, genFilePath: string, stmts: o.Statement[], exportedVars: string[],
|
||||||
preamble?: string): string;
|
preamble?: string|null): string;
|
||||||
}
|
}
|
||||||
|
|
||||||
class _EmittedLine {
|
class _EmittedLine {
|
||||||
parts: string[] = [];
|
parts: string[] = [];
|
||||||
srcSpans: ParseSourceSpan[] = [];
|
srcSpans: (ParseSourceSpan|null)[] = [];
|
||||||
constructor(public indent: number) {}
|
constructor(public indent: number) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -45,13 +45,13 @@ export class EmitterVisitorContext {
|
|||||||
|
|
||||||
isExportedVar(varName: string): boolean { return this._exportedVars.indexOf(varName) !== -1; }
|
isExportedVar(varName: string): boolean { return this._exportedVars.indexOf(varName) !== -1; }
|
||||||
|
|
||||||
println(from?: {sourceSpan?: ParseSourceSpan}|null, lastPart: string = ''): void {
|
println(from?: {sourceSpan: ParseSourceSpan | null}|null, lastPart: string = ''): void {
|
||||||
this.print(from, lastPart, true);
|
this.print(from || null, lastPart, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
lineIsEmpty(): boolean { return this._currentLine.parts.length === 0; }
|
lineIsEmpty(): boolean { return this._currentLine.parts.length === 0; }
|
||||||
|
|
||||||
print(from: {sourceSpan?: ParseSourceSpan}|null, part: string, newLine: boolean = false) {
|
print(from: {sourceSpan: ParseSourceSpan | null}|null, part: string, newLine: boolean = false) {
|
||||||
if (part.length > 0) {
|
if (part.length > 0) {
|
||||||
this._currentLine.parts.push(part);
|
this._currentLine.parts.push(part);
|
||||||
this._currentLine.srcSpans.push(from && from.sourceSpan || null);
|
this._currentLine.srcSpans.push(from && from.sourceSpan || null);
|
||||||
@ -79,9 +79,9 @@ export class EmitterVisitorContext {
|
|||||||
|
|
||||||
pushClass(clazz: o.ClassStmt) { this._classes.push(clazz); }
|
pushClass(clazz: o.ClassStmt) { this._classes.push(clazz); }
|
||||||
|
|
||||||
popClass(): o.ClassStmt { return this._classes.pop(); }
|
popClass(): o.ClassStmt { return this._classes.pop() !; }
|
||||||
|
|
||||||
get currentClass(): o.ClassStmt {
|
get currentClass(): o.ClassStmt|null {
|
||||||
return this._classes.length > 0 ? this._classes[this._classes.length - 1] : null;
|
return this._classes.length > 0 ? this._classes[this._classes.length - 1] : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -130,7 +130,7 @@ export class EmitterVisitorContext {
|
|||||||
}
|
}
|
||||||
|
|
||||||
while (spanIdx < spans.length) {
|
while (spanIdx < spans.length) {
|
||||||
const span = spans[spanIdx];
|
const span = spans[spanIdx] !;
|
||||||
const source = span.start.file;
|
const source = span.start.file;
|
||||||
const sourceLine = span.start.line;
|
const sourceLine = span.start.line;
|
||||||
const sourceCol = span.start.col;
|
const sourceCol = span.start.col;
|
||||||
@ -286,7 +286,7 @@ export abstract class AbstractEmitterVisitor implements o.StatementVisitor, o.Ex
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
visitReadVarExpr(ast: o.ReadVarExpr, ctx: EmitterVisitorContext): any {
|
visitReadVarExpr(ast: o.ReadVarExpr, ctx: EmitterVisitorContext): any {
|
||||||
let varName = ast.name;
|
let varName = ast.name !;
|
||||||
if (ast.builtin != null) {
|
if (ast.builtin != null) {
|
||||||
switch (ast.builtin) {
|
switch (ast.builtin) {
|
||||||
case o.BuiltinVar.Super:
|
case o.BuiltinVar.Super:
|
||||||
@ -296,10 +296,10 @@ export abstract class AbstractEmitterVisitor implements o.StatementVisitor, o.Ex
|
|||||||
varName = 'this';
|
varName = 'this';
|
||||||
break;
|
break;
|
||||||
case o.BuiltinVar.CatchError:
|
case o.BuiltinVar.CatchError:
|
||||||
varName = CATCH_ERROR_VAR.name;
|
varName = CATCH_ERROR_VAR.name !;
|
||||||
break;
|
break;
|
||||||
case o.BuiltinVar.CatchStack:
|
case o.BuiltinVar.CatchStack:
|
||||||
varName = CATCH_STACK_VAR.name;
|
varName = CATCH_STACK_VAR.name !;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
throw new Error(`Unknown builtin variable ${ast.builtin}`);
|
throw new Error(`Unknown builtin variable ${ast.builtin}`);
|
||||||
@ -335,7 +335,7 @@ export abstract class AbstractEmitterVisitor implements o.StatementVisitor, o.Ex
|
|||||||
ctx.print(ast, '? ');
|
ctx.print(ast, '? ');
|
||||||
ast.trueCase.visitExpression(this, ctx);
|
ast.trueCase.visitExpression(this, ctx);
|
||||||
ctx.print(ast, ': ');
|
ctx.print(ast, ': ');
|
||||||
ast.falseCase.visitExpression(this, ctx);
|
ast.falseCase !.visitExpression(this, ctx);
|
||||||
ctx.print(ast, `)`);
|
ctx.print(ast, `)`);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
@ -70,7 +70,7 @@ export abstract class AbstractJsEmitterVisitor extends AbstractEmitterVisitor {
|
|||||||
ctx.println(stmt, `};`);
|
ctx.println(stmt, `};`);
|
||||||
}
|
}
|
||||||
|
|
||||||
visitReadVarExpr(ast: o.ReadVarExpr, ctx: EmitterVisitorContext): string {
|
visitReadVarExpr(ast: o.ReadVarExpr, ctx: EmitterVisitorContext): string|null {
|
||||||
if (ast.builtin === o.BuiltinVar.This) {
|
if (ast.builtin === o.BuiltinVar.This) {
|
||||||
ctx.print(ast, 'self');
|
ctx.print(ast, 'self');
|
||||||
} else if (ast.builtin === o.BuiltinVar.Super) {
|
} else if (ast.builtin === o.BuiltinVar.Super) {
|
||||||
@ -91,10 +91,10 @@ export abstract class AbstractJsEmitterVisitor extends AbstractEmitterVisitor {
|
|||||||
ast.value.visitExpression(this, ctx);
|
ast.value.visitExpression(this, ctx);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
visitInvokeFunctionExpr(expr: o.InvokeFunctionExpr, ctx: EmitterVisitorContext): string {
|
visitInvokeFunctionExpr(expr: o.InvokeFunctionExpr, ctx: EmitterVisitorContext): string|null {
|
||||||
const fnExpr = expr.fn;
|
const fnExpr = expr.fn;
|
||||||
if (fnExpr instanceof o.ReadVarExpr && fnExpr.builtin === o.BuiltinVar.Super) {
|
if (fnExpr instanceof o.ReadVarExpr && fnExpr.builtin === o.BuiltinVar.Super) {
|
||||||
ctx.currentClass.parent.visitExpression(this, ctx);
|
ctx.currentClass !.parent !.visitExpression(this, ctx);
|
||||||
ctx.print(expr, `.call(this`);
|
ctx.print(expr, `.call(this`);
|
||||||
if (expr.args.length > 0) {
|
if (expr.args.length > 0) {
|
||||||
ctx.print(expr, `, `);
|
ctx.print(expr, `, `);
|
||||||
|
@ -31,16 +31,16 @@ export function createClassStmt(config: {
|
|||||||
new o.ClassMethod(null, config.ctorParams || [], superCtorStmts.concat(builder.ctorStmts));
|
new o.ClassMethod(null, config.ctorParams || [], superCtorStmts.concat(builder.ctorStmts));
|
||||||
|
|
||||||
return new o.ClassStmt(
|
return new o.ClassStmt(
|
||||||
config.name, config.parent, builder.fields, builder.getters, ctor, builder.methods,
|
config.name, config.parent || null, builder.fields, builder.getters, ctor, builder.methods,
|
||||||
config.modifiers || [], config.sourceSpan);
|
config.modifiers || [], config.sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
function concatClassBuilderParts(builders: ClassBuilderPart[]) {
|
function concatClassBuilderParts(builders: ClassBuilderPart[]) {
|
||||||
return {
|
return {
|
||||||
fields: [].concat(...builders.map(builder => builder.fields || [])),
|
fields: [].concat(...(builders.map((builder => builder.fields || [])) as any)),
|
||||||
methods: [].concat(...builders.map(builder => builder.methods || [])),
|
methods: [].concat(...(builders.map(builder => builder.methods || []) as any)),
|
||||||
getters: [].concat(...builders.map(builder => builder.getters || [])),
|
getters: [].concat(...(builders.map(builder => builder.getters || []) as any)),
|
||||||
ctorStmts: [].concat(...builders.map(builder => builder.ctorStmts || [])),
|
ctorStmts: [].concat(...(builders.map(builder => builder.ctorStmts || []) as any)),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -16,14 +16,14 @@ export enum TypeModifier {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export abstract class Type {
|
export abstract class Type {
|
||||||
constructor(public modifiers: TypeModifier[] = null) {
|
constructor(public modifiers: TypeModifier[]|null = null) {
|
||||||
if (!modifiers) {
|
if (!modifiers) {
|
||||||
this.modifiers = [];
|
this.modifiers = [];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
abstract visitType(visitor: TypeVisitor, context: any): any;
|
abstract visitType(visitor: TypeVisitor, context: any): any;
|
||||||
|
|
||||||
hasModifier(modifier: TypeModifier): boolean { return this.modifiers.indexOf(modifier) !== -1; }
|
hasModifier(modifier: TypeModifier): boolean { return this.modifiers !.indexOf(modifier) !== -1; }
|
||||||
}
|
}
|
||||||
|
|
||||||
export enum BuiltinTypeName {
|
export enum BuiltinTypeName {
|
||||||
@ -37,14 +37,16 @@ export enum BuiltinTypeName {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class BuiltinType extends Type {
|
export class BuiltinType extends Type {
|
||||||
constructor(public name: BuiltinTypeName, modifiers: TypeModifier[] = null) { super(modifiers); }
|
constructor(public name: BuiltinTypeName, modifiers: TypeModifier[]|null = null) {
|
||||||
|
super(modifiers);
|
||||||
|
}
|
||||||
visitType(visitor: TypeVisitor, context: any): any {
|
visitType(visitor: TypeVisitor, context: any): any {
|
||||||
return visitor.visitBuiltintType(this, context);
|
return visitor.visitBuiltintType(this, context);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class ExpressionType extends Type {
|
export class ExpressionType extends Type {
|
||||||
constructor(public value: Expression, modifiers: TypeModifier[] = null) { super(modifiers); }
|
constructor(public value: Expression, modifiers: TypeModifier[]|null = null) { super(modifiers); }
|
||||||
visitType(visitor: TypeVisitor, context: any): any {
|
visitType(visitor: TypeVisitor, context: any): any {
|
||||||
return visitor.visitExpressionType(this, context);
|
return visitor.visitExpressionType(this, context);
|
||||||
}
|
}
|
||||||
@ -52,7 +54,7 @@ export class ExpressionType extends Type {
|
|||||||
|
|
||||||
|
|
||||||
export class ArrayType extends Type {
|
export class ArrayType extends Type {
|
||||||
constructor(public of : Type, modifiers: TypeModifier[] = null) { super(modifiers); }
|
constructor(public of : Type, modifiers: TypeModifier[]|null = null) { super(modifiers); }
|
||||||
visitType(visitor: TypeVisitor, context: any): any {
|
visitType(visitor: TypeVisitor, context: any): any {
|
||||||
return visitor.visitArrayType(this, context);
|
return visitor.visitArrayType(this, context);
|
||||||
}
|
}
|
||||||
@ -60,7 +62,11 @@ export class ArrayType extends Type {
|
|||||||
|
|
||||||
|
|
||||||
export class MapType extends Type {
|
export class MapType extends Type {
|
||||||
constructor(public valueType: Type, modifiers: TypeModifier[] = null) { super(modifiers); }
|
public valueType: Type|null;
|
||||||
|
constructor(valueType: Type|null|undefined, modifiers: TypeModifier[]|null = null) {
|
||||||
|
super(modifiers);
|
||||||
|
this.valueType = valueType || null;
|
||||||
|
}
|
||||||
visitType(visitor: TypeVisitor, context: any): any { return visitor.visitMapType(this, context); }
|
visitType(visitor: TypeVisitor, context: any): any { return visitor.visitMapType(this, context); }
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -101,92 +107,99 @@ export enum BinaryOperator {
|
|||||||
|
|
||||||
|
|
||||||
export abstract class Expression {
|
export abstract class Expression {
|
||||||
constructor(public type: Type, public sourceSpan?: ParseSourceSpan) {}
|
public type: Type|null;
|
||||||
|
public sourceSpan: ParseSourceSpan|null;
|
||||||
|
|
||||||
|
constructor(type: Type|null|undefined, sourceSpan?: ParseSourceSpan|null) {
|
||||||
|
this.type = type || null;
|
||||||
|
this.sourceSpan = sourceSpan || null;
|
||||||
|
}
|
||||||
|
|
||||||
abstract visitExpression(visitor: ExpressionVisitor, context: any): any;
|
abstract visitExpression(visitor: ExpressionVisitor, context: any): any;
|
||||||
|
|
||||||
prop(name: string, sourceSpan?: ParseSourceSpan): ReadPropExpr {
|
prop(name: string, sourceSpan?: ParseSourceSpan|null): ReadPropExpr {
|
||||||
return new ReadPropExpr(this, name, null, sourceSpan);
|
return new ReadPropExpr(this, name, null, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
key(index: Expression, type: Type = null, sourceSpan?: ParseSourceSpan): ReadKeyExpr {
|
key(index: Expression, type?: Type|null, sourceSpan?: ParseSourceSpan|null): ReadKeyExpr {
|
||||||
return new ReadKeyExpr(this, index, type, sourceSpan);
|
return new ReadKeyExpr(this, index, type, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
callMethod(name: string|BuiltinMethod, params: Expression[], sourceSpan?: ParseSourceSpan):
|
callMethod(name: string|BuiltinMethod, params: Expression[], sourceSpan?: ParseSourceSpan|null):
|
||||||
InvokeMethodExpr {
|
InvokeMethodExpr {
|
||||||
return new InvokeMethodExpr(this, name, params, null, sourceSpan);
|
return new InvokeMethodExpr(this, name, params, null, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
callFn(params: Expression[], sourceSpan?: ParseSourceSpan): InvokeFunctionExpr {
|
callFn(params: Expression[], sourceSpan?: ParseSourceSpan|null): InvokeFunctionExpr {
|
||||||
return new InvokeFunctionExpr(this, params, null, sourceSpan);
|
return new InvokeFunctionExpr(this, params, null, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
instantiate(params: Expression[], type: Type = null, sourceSpan?: ParseSourceSpan):
|
instantiate(params: Expression[], type?: Type|null, sourceSpan?: ParseSourceSpan|null):
|
||||||
InstantiateExpr {
|
InstantiateExpr {
|
||||||
return new InstantiateExpr(this, params, type, sourceSpan);
|
return new InstantiateExpr(this, params, type, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
conditional(trueCase: Expression, falseCase: Expression = null, sourceSpan?: ParseSourceSpan):
|
conditional(
|
||||||
ConditionalExpr {
|
trueCase: Expression, falseCase: Expression|null = null,
|
||||||
|
sourceSpan?: ParseSourceSpan|null): ConditionalExpr {
|
||||||
return new ConditionalExpr(this, trueCase, falseCase, null, sourceSpan);
|
return new ConditionalExpr(this, trueCase, falseCase, null, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
equals(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
equals(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.Equals, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.Equals, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
notEquals(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
notEquals(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.NotEquals, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.NotEquals, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
identical(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
identical(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.Identical, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.Identical, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
notIdentical(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
notIdentical(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.NotIdentical, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.NotIdentical, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
minus(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
minus(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.Minus, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.Minus, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
plus(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
plus(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.Plus, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.Plus, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
divide(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
divide(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.Divide, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.Divide, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
multiply(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
multiply(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.Multiply, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.Multiply, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
modulo(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
modulo(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.Modulo, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.Modulo, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
and(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
and(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.And, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.And, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
or(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
or(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.Or, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.Or, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
lower(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
lower(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.Lower, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.Lower, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
lowerEquals(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
lowerEquals(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.LowerEquals, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.LowerEquals, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
bigger(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
bigger(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.Bigger, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.Bigger, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
biggerEquals(rhs: Expression, sourceSpan?: ParseSourceSpan): BinaryOperatorExpr {
|
biggerEquals(rhs: Expression, sourceSpan?: ParseSourceSpan|null): BinaryOperatorExpr {
|
||||||
return new BinaryOperatorExpr(BinaryOperator.BiggerEquals, this, rhs, null, sourceSpan);
|
return new BinaryOperatorExpr(BinaryOperator.BiggerEquals, this, rhs, null, sourceSpan);
|
||||||
}
|
}
|
||||||
isBlank(sourceSpan?: ParseSourceSpan): Expression {
|
isBlank(sourceSpan?: ParseSourceSpan|null): Expression {
|
||||||
// Note: We use equals by purpose here to compare to null and undefined in JS.
|
// Note: We use equals by purpose here to compare to null and undefined in JS.
|
||||||
// We use the typed null to allow strictNullChecks to narrow types.
|
// We use the typed null to allow strictNullChecks to narrow types.
|
||||||
return this.equals(TYPED_NULL_EXPR, sourceSpan);
|
return this.equals(TYPED_NULL_EXPR, sourceSpan);
|
||||||
}
|
}
|
||||||
cast(type: Type, sourceSpan?: ParseSourceSpan): Expression {
|
cast(type: Type, sourceSpan?: ParseSourceSpan|null): Expression {
|
||||||
return new CastExpr(this, type, sourceSpan);
|
return new CastExpr(this, type, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
toStmt(): Statement { return new ExpressionStatement(this); }
|
toStmt(): Statement { return new ExpressionStatement(this, null); }
|
||||||
}
|
}
|
||||||
|
|
||||||
export enum BuiltinVar {
|
export enum BuiltinVar {
|
||||||
@ -197,10 +210,10 @@ export enum BuiltinVar {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class ReadVarExpr extends Expression {
|
export class ReadVarExpr extends Expression {
|
||||||
public name: string;
|
public name: string|null;
|
||||||
public builtin: BuiltinVar;
|
public builtin: BuiltinVar|null;
|
||||||
|
|
||||||
constructor(name: string|BuiltinVar, type: Type = null, sourceSpan?: ParseSourceSpan) {
|
constructor(name: string|BuiltinVar, type?: Type|null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
if (typeof name === 'string') {
|
if (typeof name === 'string') {
|
||||||
this.name = name;
|
this.name = name;
|
||||||
@ -215,6 +228,9 @@ export class ReadVarExpr extends Expression {
|
|||||||
}
|
}
|
||||||
|
|
||||||
set(value: Expression): WriteVarExpr {
|
set(value: Expression): WriteVarExpr {
|
||||||
|
if (!this.name) {
|
||||||
|
throw new Error(`Built in variable ${this.builtin} can not be assigned to.`)
|
||||||
|
}
|
||||||
return new WriteVarExpr(this.name, value, null, this.sourceSpan);
|
return new WriteVarExpr(this.name, value, null, this.sourceSpan);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -223,7 +239,7 @@ export class ReadVarExpr extends Expression {
|
|||||||
export class WriteVarExpr extends Expression {
|
export class WriteVarExpr extends Expression {
|
||||||
public value: Expression;
|
public value: Expression;
|
||||||
constructor(
|
constructor(
|
||||||
public name: string, value: Expression, type: Type = null, sourceSpan?: ParseSourceSpan) {
|
public name: string, value: Expression, type?: Type|null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type || value.type, sourceSpan);
|
super(type || value.type, sourceSpan);
|
||||||
this.value = value;
|
this.value = value;
|
||||||
}
|
}
|
||||||
@ -232,7 +248,7 @@ export class WriteVarExpr extends Expression {
|
|||||||
return visitor.visitWriteVarExpr(this, context);
|
return visitor.visitWriteVarExpr(this, context);
|
||||||
}
|
}
|
||||||
|
|
||||||
toDeclStmt(type: Type = null, modifiers: StmtModifier[] = null): DeclareVarStmt {
|
toDeclStmt(type?: Type|null, modifiers?: StmtModifier[]|null): DeclareVarStmt {
|
||||||
return new DeclareVarStmt(this.name, this.value, type, modifiers, this.sourceSpan);
|
return new DeclareVarStmt(this.name, this.value, type, modifiers, this.sourceSpan);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -241,8 +257,8 @@ export class WriteVarExpr extends Expression {
|
|||||||
export class WriteKeyExpr extends Expression {
|
export class WriteKeyExpr extends Expression {
|
||||||
public value: Expression;
|
public value: Expression;
|
||||||
constructor(
|
constructor(
|
||||||
public receiver: Expression, public index: Expression, value: Expression, type: Type = null,
|
public receiver: Expression, public index: Expression, value: Expression, type?: Type|null,
|
||||||
sourceSpan?: ParseSourceSpan) {
|
sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type || value.type, sourceSpan);
|
super(type || value.type, sourceSpan);
|
||||||
this.value = value;
|
this.value = value;
|
||||||
}
|
}
|
||||||
@ -255,8 +271,8 @@ export class WriteKeyExpr extends Expression {
|
|||||||
export class WritePropExpr extends Expression {
|
export class WritePropExpr extends Expression {
|
||||||
public value: Expression;
|
public value: Expression;
|
||||||
constructor(
|
constructor(
|
||||||
public receiver: Expression, public name: string, value: Expression, type: Type = null,
|
public receiver: Expression, public name: string, value: Expression, type?: Type|null,
|
||||||
sourceSpan?: ParseSourceSpan) {
|
sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type || value.type, sourceSpan);
|
super(type || value.type, sourceSpan);
|
||||||
this.value = value;
|
this.value = value;
|
||||||
}
|
}
|
||||||
@ -272,11 +288,11 @@ export enum BuiltinMethod {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class InvokeMethodExpr extends Expression {
|
export class InvokeMethodExpr extends Expression {
|
||||||
public name: string;
|
public name: string|null;
|
||||||
public builtin: BuiltinMethod;
|
public builtin: BuiltinMethod|null;
|
||||||
constructor(
|
constructor(
|
||||||
public receiver: Expression, method: string|BuiltinMethod, public args: Expression[],
|
public receiver: Expression, method: string|BuiltinMethod, public args: Expression[],
|
||||||
type: Type = null, sourceSpan?: ParseSourceSpan) {
|
type?: Type|null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
if (typeof method === 'string') {
|
if (typeof method === 'string') {
|
||||||
this.name = method;
|
this.name = method;
|
||||||
@ -294,8 +310,8 @@ export class InvokeMethodExpr extends Expression {
|
|||||||
|
|
||||||
export class InvokeFunctionExpr extends Expression {
|
export class InvokeFunctionExpr extends Expression {
|
||||||
constructor(
|
constructor(
|
||||||
public fn: Expression, public args: Expression[], type: Type = null,
|
public fn: Expression, public args: Expression[], type?: Type|null,
|
||||||
sourceSpan?: ParseSourceSpan) {
|
sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
}
|
}
|
||||||
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
||||||
@ -306,8 +322,8 @@ export class InvokeFunctionExpr extends Expression {
|
|||||||
|
|
||||||
export class InstantiateExpr extends Expression {
|
export class InstantiateExpr extends Expression {
|
||||||
constructor(
|
constructor(
|
||||||
public classExpr: Expression, public args: Expression[], type?: Type,
|
public classExpr: Expression, public args: Expression[], type?: Type|null,
|
||||||
sourceSpan?: ParseSourceSpan) {
|
sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
}
|
}
|
||||||
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
||||||
@ -317,7 +333,7 @@ export class InstantiateExpr extends Expression {
|
|||||||
|
|
||||||
|
|
||||||
export class LiteralExpr extends Expression {
|
export class LiteralExpr extends Expression {
|
||||||
constructor(public value: any, type: Type = null, sourceSpan?: ParseSourceSpan) {
|
constructor(public value: any, type?: Type|null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
}
|
}
|
||||||
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
||||||
@ -328,8 +344,8 @@ export class LiteralExpr extends Expression {
|
|||||||
|
|
||||||
export class ExternalExpr extends Expression {
|
export class ExternalExpr extends Expression {
|
||||||
constructor(
|
constructor(
|
||||||
public value: CompileIdentifierMetadata, type: Type = null, public typeParams: Type[] = null,
|
public value: CompileIdentifierMetadata, type?: Type|null,
|
||||||
sourceSpan?: ParseSourceSpan) {
|
public typeParams: Type[]|null = null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
}
|
}
|
||||||
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
||||||
@ -341,8 +357,8 @@ export class ExternalExpr extends Expression {
|
|||||||
export class ConditionalExpr extends Expression {
|
export class ConditionalExpr extends Expression {
|
||||||
public trueCase: Expression;
|
public trueCase: Expression;
|
||||||
constructor(
|
constructor(
|
||||||
public condition: Expression, trueCase: Expression, public falseCase: Expression = null,
|
public condition: Expression, trueCase: Expression, public falseCase: Expression|null = null,
|
||||||
type: Type = null, sourceSpan?: ParseSourceSpan) {
|
type?: Type|null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type || trueCase.type, sourceSpan);
|
super(type || trueCase.type, sourceSpan);
|
||||||
this.trueCase = trueCase;
|
this.trueCase = trueCase;
|
||||||
}
|
}
|
||||||
@ -353,7 +369,7 @@ export class ConditionalExpr extends Expression {
|
|||||||
|
|
||||||
|
|
||||||
export class NotExpr extends Expression {
|
export class NotExpr extends Expression {
|
||||||
constructor(public condition: Expression, sourceSpan?: ParseSourceSpan) {
|
constructor(public condition: Expression, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(BOOL_TYPE, sourceSpan);
|
super(BOOL_TYPE, sourceSpan);
|
||||||
}
|
}
|
||||||
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
||||||
@ -362,7 +378,7 @@ export class NotExpr extends Expression {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class CastExpr extends Expression {
|
export class CastExpr extends Expression {
|
||||||
constructor(public value: Expression, type: Type, sourceSpan?: ParseSourceSpan) {
|
constructor(public value: Expression, type?: Type|null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
}
|
}
|
||||||
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
||||||
@ -372,21 +388,21 @@ export class CastExpr extends Expression {
|
|||||||
|
|
||||||
|
|
||||||
export class FnParam {
|
export class FnParam {
|
||||||
constructor(public name: string, public type: Type = null) {}
|
constructor(public name: string, public type: Type|null = null) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
export class FunctionExpr extends Expression {
|
export class FunctionExpr extends Expression {
|
||||||
constructor(
|
constructor(
|
||||||
public params: FnParam[], public statements: Statement[], type: Type = null,
|
public params: FnParam[], public statements: Statement[], type?: Type|null,
|
||||||
sourceSpan?: ParseSourceSpan) {
|
sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
}
|
}
|
||||||
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
||||||
return visitor.visitFunctionExpr(this, context);
|
return visitor.visitFunctionExpr(this, context);
|
||||||
}
|
}
|
||||||
|
|
||||||
toDeclStmt(name: string, modifiers: StmtModifier[] = null): DeclareFunctionStmt {
|
toDeclStmt(name: string, modifiers: StmtModifier[]|null = null): DeclareFunctionStmt {
|
||||||
return new DeclareFunctionStmt(
|
return new DeclareFunctionStmt(
|
||||||
name, this.params, this.statements, this.type, modifiers, this.sourceSpan);
|
name, this.params, this.statements, this.type, modifiers, this.sourceSpan);
|
||||||
}
|
}
|
||||||
@ -396,8 +412,8 @@ export class FunctionExpr extends Expression {
|
|||||||
export class BinaryOperatorExpr extends Expression {
|
export class BinaryOperatorExpr extends Expression {
|
||||||
public lhs: Expression;
|
public lhs: Expression;
|
||||||
constructor(
|
constructor(
|
||||||
public operator: BinaryOperator, lhs: Expression, public rhs: Expression, type: Type = null,
|
public operator: BinaryOperator, lhs: Expression, public rhs: Expression, type?: Type|null,
|
||||||
sourceSpan?: ParseSourceSpan) {
|
sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type || lhs.type, sourceSpan);
|
super(type || lhs.type, sourceSpan);
|
||||||
this.lhs = lhs;
|
this.lhs = lhs;
|
||||||
}
|
}
|
||||||
@ -409,8 +425,8 @@ export class BinaryOperatorExpr extends Expression {
|
|||||||
|
|
||||||
export class ReadPropExpr extends Expression {
|
export class ReadPropExpr extends Expression {
|
||||||
constructor(
|
constructor(
|
||||||
public receiver: Expression, public name: string, type: Type = null,
|
public receiver: Expression, public name: string, type?: Type|null,
|
||||||
sourceSpan?: ParseSourceSpan) {
|
sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
}
|
}
|
||||||
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
||||||
@ -424,8 +440,8 @@ export class ReadPropExpr extends Expression {
|
|||||||
|
|
||||||
export class ReadKeyExpr extends Expression {
|
export class ReadKeyExpr extends Expression {
|
||||||
constructor(
|
constructor(
|
||||||
public receiver: Expression, public index: Expression, type: Type = null,
|
public receiver: Expression, public index: Expression, type?: Type|null,
|
||||||
sourceSpan?: ParseSourceSpan) {
|
sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
}
|
}
|
||||||
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
||||||
@ -439,7 +455,7 @@ export class ReadKeyExpr extends Expression {
|
|||||||
|
|
||||||
export class LiteralArrayExpr extends Expression {
|
export class LiteralArrayExpr extends Expression {
|
||||||
public entries: Expression[];
|
public entries: Expression[];
|
||||||
constructor(entries: Expression[], type: Type = null, sourceSpan?: ParseSourceSpan) {
|
constructor(entries: Expression[], type?: Type|null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
this.entries = entries;
|
this.entries = entries;
|
||||||
}
|
}
|
||||||
@ -453,9 +469,9 @@ export class LiteralMapEntry {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class LiteralMapExpr extends Expression {
|
export class LiteralMapExpr extends Expression {
|
||||||
public valueType: Type = null;
|
public valueType: Type|null = null;
|
||||||
constructor(
|
constructor(
|
||||||
public entries: LiteralMapEntry[], type: MapType = null, sourceSpan?: ParseSourceSpan) {
|
public entries: LiteralMapEntry[], type?: MapType|null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(type, sourceSpan);
|
super(type, sourceSpan);
|
||||||
if (type) {
|
if (type) {
|
||||||
this.valueType = type.valueType;
|
this.valueType = type.valueType;
|
||||||
@ -467,7 +483,7 @@ export class LiteralMapExpr extends Expression {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class CommaExpr extends Expression {
|
export class CommaExpr extends Expression {
|
||||||
constructor(public parts: Expression[], sourceSpan?: ParseSourceSpan) {
|
constructor(public parts: Expression[], sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(parts[parts.length - 1].type, sourceSpan);
|
super(parts[parts.length - 1].type, sourceSpan);
|
||||||
}
|
}
|
||||||
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
visitExpression(visitor: ExpressionVisitor, context: any): any {
|
||||||
@ -497,12 +513,12 @@ export interface ExpressionVisitor {
|
|||||||
visitCommaExpr(ast: CommaExpr, context: any): any;
|
visitCommaExpr(ast: CommaExpr, context: any): any;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const THIS_EXPR = new ReadVarExpr(BuiltinVar.This);
|
export const THIS_EXPR = new ReadVarExpr(BuiltinVar.This, null, null);
|
||||||
export const SUPER_EXPR = new ReadVarExpr(BuiltinVar.Super);
|
export const SUPER_EXPR = new ReadVarExpr(BuiltinVar.Super, null, null);
|
||||||
export const CATCH_ERROR_VAR = new ReadVarExpr(BuiltinVar.CatchError);
|
export const CATCH_ERROR_VAR = new ReadVarExpr(BuiltinVar.CatchError, null, null);
|
||||||
export const CATCH_STACK_VAR = new ReadVarExpr(BuiltinVar.CatchStack);
|
export const CATCH_STACK_VAR = new ReadVarExpr(BuiltinVar.CatchStack, null, null);
|
||||||
export const NULL_EXPR = new LiteralExpr(null, null);
|
export const NULL_EXPR = new LiteralExpr(null, null, null);
|
||||||
export const TYPED_NULL_EXPR = new LiteralExpr(null, INFERRED_TYPE);
|
export const TYPED_NULL_EXPR = new LiteralExpr(null, INFERRED_TYPE, null);
|
||||||
|
|
||||||
//// Statements
|
//// Statements
|
||||||
export enum StmtModifier {
|
export enum StmtModifier {
|
||||||
@ -511,23 +527,24 @@ export enum StmtModifier {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export abstract class Statement {
|
export abstract class Statement {
|
||||||
constructor(public modifiers: StmtModifier[] = null, public sourceSpan?: ParseSourceSpan) {
|
public modifiers: StmtModifier[];
|
||||||
if (!modifiers) {
|
public sourceSpan: ParseSourceSpan|null;
|
||||||
this.modifiers = [];
|
constructor(modifiers?: StmtModifier[]|null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
}
|
this.modifiers = modifiers || [];
|
||||||
|
this.sourceSpan = sourceSpan || null;
|
||||||
}
|
}
|
||||||
|
|
||||||
abstract visitStatement(visitor: StatementVisitor, context: any): any;
|
abstract visitStatement(visitor: StatementVisitor, context: any): any;
|
||||||
|
|
||||||
hasModifier(modifier: StmtModifier): boolean { return this.modifiers.indexOf(modifier) !== -1; }
|
hasModifier(modifier: StmtModifier): boolean { return this.modifiers !.indexOf(modifier) !== -1; }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
export class DeclareVarStmt extends Statement {
|
export class DeclareVarStmt extends Statement {
|
||||||
public type: Type;
|
public type: Type|null;
|
||||||
constructor(
|
constructor(
|
||||||
public name: string, public value: Expression, type: Type = null,
|
public name: string, public value: Expression, type?: Type|null,
|
||||||
modifiers: StmtModifier[] = null, sourceSpan?: ParseSourceSpan) {
|
modifiers: StmtModifier[]|null = null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(modifiers, sourceSpan);
|
super(modifiers, sourceSpan);
|
||||||
this.type = type || value.type;
|
this.type = type || value.type;
|
||||||
}
|
}
|
||||||
@ -538,10 +555,12 @@ export class DeclareVarStmt extends Statement {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class DeclareFunctionStmt extends Statement {
|
export class DeclareFunctionStmt extends Statement {
|
||||||
|
public type: Type|null;
|
||||||
constructor(
|
constructor(
|
||||||
public name: string, public params: FnParam[], public statements: Statement[],
|
public name: string, public params: FnParam[], public statements: Statement[],
|
||||||
public type: Type = null, modifiers: StmtModifier[] = null, sourceSpan?: ParseSourceSpan) {
|
type?: Type|null, modifiers: StmtModifier[]|null = null, sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(modifiers, sourceSpan);
|
super(modifiers, sourceSpan);
|
||||||
|
this.type = type || null;
|
||||||
}
|
}
|
||||||
|
|
||||||
visitStatement(visitor: StatementVisitor, context: any): any {
|
visitStatement(visitor: StatementVisitor, context: any): any {
|
||||||
@ -550,7 +569,9 @@ export class DeclareFunctionStmt extends Statement {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class ExpressionStatement extends Statement {
|
export class ExpressionStatement extends Statement {
|
||||||
constructor(public expr: Expression, sourceSpan?: ParseSourceSpan) { super(null, sourceSpan); }
|
constructor(public expr: Expression, sourceSpan?: ParseSourceSpan|null) {
|
||||||
|
super(null, sourceSpan);
|
||||||
|
}
|
||||||
|
|
||||||
visitStatement(visitor: StatementVisitor, context: any): any {
|
visitStatement(visitor: StatementVisitor, context: any): any {
|
||||||
return visitor.visitExpressionStmt(this, context);
|
return visitor.visitExpressionStmt(this, context);
|
||||||
@ -559,23 +580,27 @@ export class ExpressionStatement extends Statement {
|
|||||||
|
|
||||||
|
|
||||||
export class ReturnStatement extends Statement {
|
export class ReturnStatement extends Statement {
|
||||||
constructor(public value: Expression, sourceSpan?: ParseSourceSpan) { super(null, sourceSpan); }
|
constructor(public value: Expression, sourceSpan?: ParseSourceSpan|null) {
|
||||||
|
super(null, sourceSpan);
|
||||||
|
}
|
||||||
visitStatement(visitor: StatementVisitor, context: any): any {
|
visitStatement(visitor: StatementVisitor, context: any): any {
|
||||||
return visitor.visitReturnStmt(this, context);
|
return visitor.visitReturnStmt(this, context);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class AbstractClassPart {
|
export class AbstractClassPart {
|
||||||
constructor(public type: Type = null, public modifiers: StmtModifier[]) {
|
public type: Type|null;
|
||||||
|
constructor(type: Type|null|undefined, public modifiers: StmtModifier[]|null) {
|
||||||
if (!modifiers) {
|
if (!modifiers) {
|
||||||
this.modifiers = [];
|
this.modifiers = [];
|
||||||
}
|
}
|
||||||
|
this.type = type || null;
|
||||||
}
|
}
|
||||||
hasModifier(modifier: StmtModifier): boolean { return this.modifiers.indexOf(modifier) !== -1; }
|
hasModifier(modifier: StmtModifier): boolean { return this.modifiers !.indexOf(modifier) !== -1; }
|
||||||
}
|
}
|
||||||
|
|
||||||
export class ClassField extends AbstractClassPart {
|
export class ClassField extends AbstractClassPart {
|
||||||
constructor(public name: string, type: Type = null, modifiers: StmtModifier[] = null) {
|
constructor(public name: string, type?: Type|null, modifiers: StmtModifier[]|null = null) {
|
||||||
super(type, modifiers);
|
super(type, modifiers);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -583,8 +608,8 @@ export class ClassField extends AbstractClassPart {
|
|||||||
|
|
||||||
export class ClassMethod extends AbstractClassPart {
|
export class ClassMethod extends AbstractClassPart {
|
||||||
constructor(
|
constructor(
|
||||||
public name: string, public params: FnParam[], public body: Statement[], type: Type = null,
|
public name: string|null, public params: FnParam[], public body: Statement[],
|
||||||
modifiers: StmtModifier[] = null) {
|
type?: Type|null, modifiers: StmtModifier[]|null = null) {
|
||||||
super(type, modifiers);
|
super(type, modifiers);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -592,8 +617,8 @@ export class ClassMethod extends AbstractClassPart {
|
|||||||
|
|
||||||
export class ClassGetter extends AbstractClassPart {
|
export class ClassGetter extends AbstractClassPart {
|
||||||
constructor(
|
constructor(
|
||||||
public name: string, public body: Statement[], type: Type = null,
|
public name: string, public body: Statement[], type?: Type|null,
|
||||||
modifiers: StmtModifier[] = null) {
|
modifiers: StmtModifier[]|null = null) {
|
||||||
super(type, modifiers);
|
super(type, modifiers);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -601,10 +626,10 @@ export class ClassGetter extends AbstractClassPart {
|
|||||||
|
|
||||||
export class ClassStmt extends Statement {
|
export class ClassStmt extends Statement {
|
||||||
constructor(
|
constructor(
|
||||||
public name: string, public parent: Expression, public fields: ClassField[],
|
public name: string, public parent: Expression|null, public fields: ClassField[],
|
||||||
public getters: ClassGetter[], public constructorMethod: ClassMethod,
|
public getters: ClassGetter[], public constructorMethod: ClassMethod,
|
||||||
public methods: ClassMethod[], modifiers: StmtModifier[] = null,
|
public methods: ClassMethod[], modifiers: StmtModifier[]|null = null,
|
||||||
sourceSpan?: ParseSourceSpan) {
|
sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(modifiers, sourceSpan);
|
super(modifiers, sourceSpan);
|
||||||
}
|
}
|
||||||
visitStatement(visitor: StatementVisitor, context: any): any {
|
visitStatement(visitor: StatementVisitor, context: any): any {
|
||||||
@ -616,7 +641,7 @@ export class ClassStmt extends Statement {
|
|||||||
export class IfStmt extends Statement {
|
export class IfStmt extends Statement {
|
||||||
constructor(
|
constructor(
|
||||||
public condition: Expression, public trueCase: Statement[],
|
public condition: Expression, public trueCase: Statement[],
|
||||||
public falseCase: Statement[] = [], sourceSpan?: ParseSourceSpan) {
|
public falseCase: Statement[] = [], sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(null, sourceSpan);
|
super(null, sourceSpan);
|
||||||
}
|
}
|
||||||
visitStatement(visitor: StatementVisitor, context: any): any {
|
visitStatement(visitor: StatementVisitor, context: any): any {
|
||||||
@ -626,7 +651,9 @@ export class IfStmt extends Statement {
|
|||||||
|
|
||||||
|
|
||||||
export class CommentStmt extends Statement {
|
export class CommentStmt extends Statement {
|
||||||
constructor(public comment: string, sourceSpan?: ParseSourceSpan) { super(null, sourceSpan); }
|
constructor(public comment: string, sourceSpan?: ParseSourceSpan|null) {
|
||||||
|
super(null, sourceSpan);
|
||||||
|
}
|
||||||
visitStatement(visitor: StatementVisitor, context: any): any {
|
visitStatement(visitor: StatementVisitor, context: any): any {
|
||||||
return visitor.visitCommentStmt(this, context);
|
return visitor.visitCommentStmt(this, context);
|
||||||
}
|
}
|
||||||
@ -635,7 +662,8 @@ export class CommentStmt extends Statement {
|
|||||||
|
|
||||||
export class TryCatchStmt extends Statement {
|
export class TryCatchStmt extends Statement {
|
||||||
constructor(
|
constructor(
|
||||||
public bodyStmts: Statement[], public catchStmts: Statement[], sourceSpan?: ParseSourceSpan) {
|
public bodyStmts: Statement[], public catchStmts: Statement[],
|
||||||
|
sourceSpan?: ParseSourceSpan|null) {
|
||||||
super(null, sourceSpan);
|
super(null, sourceSpan);
|
||||||
}
|
}
|
||||||
visitStatement(visitor: StatementVisitor, context: any): any {
|
visitStatement(visitor: StatementVisitor, context: any): any {
|
||||||
@ -645,7 +673,9 @@ export class TryCatchStmt extends Statement {
|
|||||||
|
|
||||||
|
|
||||||
export class ThrowStmt extends Statement {
|
export class ThrowStmt extends Statement {
|
||||||
constructor(public error: Expression, sourceSpan?: ParseSourceSpan) { super(null, sourceSpan); }
|
constructor(public error: Expression, sourceSpan?: ParseSourceSpan|null) {
|
||||||
|
super(null, sourceSpan);
|
||||||
|
}
|
||||||
visitStatement(visitor: StatementVisitor, context: any): any {
|
visitStatement(visitor: StatementVisitor, context: any): any {
|
||||||
return visitor.visitThrowStmt(this, context);
|
return visitor.visitThrowStmt(this, context);
|
||||||
}
|
}
|
||||||
@ -697,7 +727,7 @@ export class AstTransformer implements StatementVisitor, ExpressionVisitor {
|
|||||||
const method = ast.builtin || ast.name;
|
const method = ast.builtin || ast.name;
|
||||||
return this.transformExpr(
|
return this.transformExpr(
|
||||||
new InvokeMethodExpr(
|
new InvokeMethodExpr(
|
||||||
ast.receiver.visitExpression(this, context), method,
|
ast.receiver.visitExpression(this, context), method !,
|
||||||
this.visitAllExpressions(ast.args, context), ast.type, ast.sourceSpan),
|
this.visitAllExpressions(ast.args, context), ast.type, ast.sourceSpan),
|
||||||
context);
|
context);
|
||||||
}
|
}
|
||||||
@ -729,7 +759,7 @@ export class AstTransformer implements StatementVisitor, ExpressionVisitor {
|
|||||||
new ConditionalExpr(
|
new ConditionalExpr(
|
||||||
ast.condition.visitExpression(this, context),
|
ast.condition.visitExpression(this, context),
|
||||||
ast.trueCase.visitExpression(this, context),
|
ast.trueCase.visitExpression(this, context),
|
||||||
ast.falseCase.visitExpression(this, context), ast.type, ast.sourceSpan),
|
ast.falseCase !.visitExpression(this, context), ast.type, ast.sourceSpan),
|
||||||
context);
|
context);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -784,7 +814,7 @@ export class AstTransformer implements StatementVisitor, ExpressionVisitor {
|
|||||||
const entries = ast.entries.map(
|
const entries = ast.entries.map(
|
||||||
(entry): LiteralMapEntry => new LiteralMapEntry(
|
(entry): LiteralMapEntry => new LiteralMapEntry(
|
||||||
entry.key, entry.value.visitExpression(this, context), entry.quoted, ));
|
entry.key, entry.value.visitExpression(this, context), entry.quoted, ));
|
||||||
const mapType = new MapType(ast.valueType);
|
const mapType = new MapType(ast.valueType, null);
|
||||||
return this.transformExpr(new LiteralMapExpr(entries, mapType, ast.sourceSpan), context);
|
return this.transformExpr(new LiteralMapExpr(entries, mapType, ast.sourceSpan), context);
|
||||||
}
|
}
|
||||||
visitCommaExpr(ast: CommaExpr, context: any): any {
|
visitCommaExpr(ast: CommaExpr, context: any): any {
|
||||||
@ -822,7 +852,7 @@ export class AstTransformer implements StatementVisitor, ExpressionVisitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
visitDeclareClassStmt(stmt: ClassStmt, context: any): any {
|
visitDeclareClassStmt(stmt: ClassStmt, context: any): any {
|
||||||
const parent = stmt.parent.visitExpression(this, context);
|
const parent = stmt.parent !.visitExpression(this, context);
|
||||||
const getters = stmt.getters.map(
|
const getters = stmt.getters.map(
|
||||||
getter => new ClassGetter(
|
getter => new ClassGetter(
|
||||||
getter.name, this.visitAllStatements(getter.body, context), getter.type,
|
getter.name, this.visitAllStatements(getter.body, context), getter.type,
|
||||||
@ -911,7 +941,7 @@ export class RecursiveAstVisitor implements StatementVisitor, ExpressionVisitor
|
|||||||
visitConditionalExpr(ast: ConditionalExpr, context: any): any {
|
visitConditionalExpr(ast: ConditionalExpr, context: any): any {
|
||||||
ast.condition.visitExpression(this, context);
|
ast.condition.visitExpression(this, context);
|
||||||
ast.trueCase.visitExpression(this, context);
|
ast.trueCase.visitExpression(this, context);
|
||||||
ast.falseCase.visitExpression(this, context);
|
ast.falseCase !.visitExpression(this, context);
|
||||||
return ast;
|
return ast;
|
||||||
}
|
}
|
||||||
visitNotExpr(ast: NotExpr, context: any): any {
|
visitNotExpr(ast: NotExpr, context: any): any {
|
||||||
@ -972,7 +1002,7 @@ export class RecursiveAstVisitor implements StatementVisitor, ExpressionVisitor
|
|||||||
return stmt;
|
return stmt;
|
||||||
}
|
}
|
||||||
visitDeclareClassStmt(stmt: ClassStmt, context: any): any {
|
visitDeclareClassStmt(stmt: ClassStmt, context: any): any {
|
||||||
stmt.parent.visitExpression(this, context);
|
stmt.parent !.visitExpression(this, context);
|
||||||
stmt.getters.forEach(getter => this.visitAllStatements(getter.body, context));
|
stmt.getters.forEach(getter => this.visitAllStatements(getter.body, context));
|
||||||
if (stmt.constructorMethod) {
|
if (stmt.constructorMethod) {
|
||||||
this.visitAllStatements(stmt.constructorMethod.body, context);
|
this.visitAllStatements(stmt.constructorMethod.body, context);
|
||||||
@ -1018,13 +1048,15 @@ class _ReadVarVisitor extends RecursiveAstVisitor {
|
|||||||
return stmt;
|
return stmt;
|
||||||
}
|
}
|
||||||
visitReadVarExpr(ast: ReadVarExpr, context: any): any {
|
visitReadVarExpr(ast: ReadVarExpr, context: any): any {
|
||||||
this.varNames.add(ast.name);
|
if (ast.name) {
|
||||||
|
this.varNames.add(ast.name);
|
||||||
|
}
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export function applySourceSpanToStatementIfNeeded(
|
export function applySourceSpanToStatementIfNeeded(
|
||||||
stmt: Statement, sourceSpan: ParseSourceSpan): Statement {
|
stmt: Statement, sourceSpan: ParseSourceSpan | null): Statement {
|
||||||
if (!sourceSpan) {
|
if (!sourceSpan) {
|
||||||
return stmt;
|
return stmt;
|
||||||
}
|
}
|
||||||
@ -1033,7 +1065,7 @@ export function applySourceSpanToStatementIfNeeded(
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function applySourceSpanToExpressionIfNeeded(
|
export function applySourceSpanToExpressionIfNeeded(
|
||||||
expr: Expression, sourceSpan: ParseSourceSpan): Expression {
|
expr: Expression, sourceSpan: ParseSourceSpan | null): Expression {
|
||||||
if (!sourceSpan) {
|
if (!sourceSpan) {
|
||||||
return expr;
|
return expr;
|
||||||
}
|
}
|
||||||
@ -1069,48 +1101,51 @@ class _ApplySourceSpanTransformer extends AstTransformer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function variable(
|
export function variable(
|
||||||
name: string, type: Type = null, sourceSpan?: ParseSourceSpan): ReadVarExpr {
|
name: string, type?: Type | null, sourceSpan?: ParseSourceSpan | null): ReadVarExpr {
|
||||||
return new ReadVarExpr(name, type, sourceSpan);
|
return new ReadVarExpr(name, type, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function importExpr(
|
export function importExpr(
|
||||||
id: CompileIdentifierMetadata, typeParams: Type[] = null,
|
id: CompileIdentifierMetadata, typeParams: Type[] | null = null,
|
||||||
sourceSpan?: ParseSourceSpan): ExternalExpr {
|
sourceSpan?: ParseSourceSpan | null): ExternalExpr {
|
||||||
return new ExternalExpr(id, null, typeParams, sourceSpan);
|
return new ExternalExpr(id, null, typeParams, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function importType(
|
export function importType(
|
||||||
id: CompileIdentifierMetadata, typeParams: Type[] = null,
|
id: CompileIdentifierMetadata, typeParams: Type[] | null = null,
|
||||||
typeModifiers: TypeModifier[] = null): ExpressionType {
|
typeModifiers: TypeModifier[] | null = null): ExpressionType|null {
|
||||||
return id != null ? expressionType(importExpr(id, typeParams), typeModifiers) : null;
|
return id != null ? expressionType(importExpr(id, typeParams, null), typeModifiers) : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function expressionType(
|
export function expressionType(
|
||||||
expr: Expression, typeModifiers: TypeModifier[] = null): ExpressionType {
|
expr: Expression, typeModifiers: TypeModifier[] | null = null): ExpressionType|null {
|
||||||
return expr != null ? new ExpressionType(expr, typeModifiers) : null;
|
return expr != null ? new ExpressionType(expr, typeModifiers) ! : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function literalArr(
|
export function literalArr(
|
||||||
values: Expression[], type: Type = null, sourceSpan?: ParseSourceSpan): LiteralArrayExpr {
|
values: Expression[], type?: Type | null,
|
||||||
|
sourceSpan?: ParseSourceSpan | null): LiteralArrayExpr {
|
||||||
return new LiteralArrayExpr(values, type, sourceSpan);
|
return new LiteralArrayExpr(values, type, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function literalMap(
|
export function literalMap(
|
||||||
values: [string, Expression][], type: MapType = null, quoted: boolean = false): LiteralMapExpr {
|
values: [string, Expression][], type: MapType | null = null,
|
||||||
|
quoted: boolean = false): LiteralMapExpr {
|
||||||
return new LiteralMapExpr(
|
return new LiteralMapExpr(
|
||||||
values.map(entry => new LiteralMapEntry(entry[0], entry[1], quoted)), type);
|
values.map(entry => new LiteralMapEntry(entry[0], entry[1], quoted)), type, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function not(expr: Expression, sourceSpan?: ParseSourceSpan): NotExpr {
|
export function not(expr: Expression, sourceSpan?: ParseSourceSpan | null): NotExpr {
|
||||||
return new NotExpr(expr, sourceSpan);
|
return new NotExpr(expr, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function fn(
|
export function fn(
|
||||||
params: FnParam[], body: Statement[], type: Type = null,
|
params: FnParam[], body: Statement[], type?: Type | null,
|
||||||
sourceSpan?: ParseSourceSpan): FunctionExpr {
|
sourceSpan?: ParseSourceSpan | null): FunctionExpr {
|
||||||
return new FunctionExpr(params, body, type, sourceSpan);
|
return new FunctionExpr(params, body, type, sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function literal(value: any, type: Type = null, sourceSpan?: ParseSourceSpan): LiteralExpr {
|
export function literal(
|
||||||
|
value: any, type?: Type | null, sourceSpan?: ParseSourceSpan | null): LiteralExpr {
|
||||||
return new LiteralExpr(value, type, sourceSpan);
|
return new LiteralExpr(value, type, sourceSpan);
|
||||||
}
|
}
|
||||||
|
@ -33,7 +33,7 @@ function _executeFunctionStatements(
|
|||||||
|
|
||||||
class _ExecutionContext {
|
class _ExecutionContext {
|
||||||
constructor(
|
constructor(
|
||||||
public parent: _ExecutionContext, public instance: any, public className: string,
|
public parent: _ExecutionContext|null, public instance: any, public className: string|null,
|
||||||
public vars: Map<string, any>) {}
|
public vars: Map<string, any>) {}
|
||||||
|
|
||||||
createChildWihtLocalVars(): _ExecutionContext {
|
createChildWihtLocalVars(): _ExecutionContext {
|
||||||
@ -62,7 +62,7 @@ function createDynamicClass(
|
|||||||
_classStmt.methods.forEach(function(method: o.ClassMethod) {
|
_classStmt.methods.forEach(function(method: o.ClassMethod) {
|
||||||
const paramNames = method.params.map(param => param.name);
|
const paramNames = method.params.map(param => param.name);
|
||||||
// Note: use `function` instead of arrow function to capture `this`
|
// Note: use `function` instead of arrow function to capture `this`
|
||||||
propertyDescriptors[method.name] = {
|
propertyDescriptors[method.name !] = {
|
||||||
writable: false,
|
writable: false,
|
||||||
configurable: false,
|
configurable: false,
|
||||||
value: function(...args: any[]) {
|
value: function(...args: any[]) {
|
||||||
@ -100,12 +100,12 @@ class StatementInterpreter implements o.StatementVisitor, o.ExpressionVisitor {
|
|||||||
currCtx.vars.set(expr.name, value);
|
currCtx.vars.set(expr.name, value);
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
currCtx = currCtx.parent;
|
currCtx = currCtx.parent !;
|
||||||
}
|
}
|
||||||
throw new Error(`Not declared variable ${expr.name}`);
|
throw new Error(`Not declared variable ${expr.name}`);
|
||||||
}
|
}
|
||||||
visitReadVarExpr(ast: o.ReadVarExpr, ctx: _ExecutionContext): any {
|
visitReadVarExpr(ast: o.ReadVarExpr, ctx: _ExecutionContext): any {
|
||||||
let varName = ast.name;
|
let varName = ast.name !;
|
||||||
if (ast.builtin != null) {
|
if (ast.builtin != null) {
|
||||||
switch (ast.builtin) {
|
switch (ast.builtin) {
|
||||||
case o.BuiltinVar.Super:
|
case o.BuiltinVar.Super:
|
||||||
@ -127,7 +127,7 @@ class StatementInterpreter implements o.StatementVisitor, o.ExpressionVisitor {
|
|||||||
if (currCtx.vars.has(varName)) {
|
if (currCtx.vars.has(varName)) {
|
||||||
return currCtx.vars.get(varName);
|
return currCtx.vars.get(varName);
|
||||||
}
|
}
|
||||||
currCtx = currCtx.parent;
|
currCtx = currCtx.parent !;
|
||||||
}
|
}
|
||||||
throw new Error(`Not declared variable ${varName}`);
|
throw new Error(`Not declared variable ${varName}`);
|
||||||
}
|
}
|
||||||
@ -164,7 +164,7 @@ class StatementInterpreter implements o.StatementVisitor, o.ExpressionVisitor {
|
|||||||
throw new Error(`Unknown builtin method ${expr.builtin}`);
|
throw new Error(`Unknown builtin method ${expr.builtin}`);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
result = receiver[expr.name].apply(receiver, args);
|
result = receiver[expr.name !].apply(receiver, args);
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@ -312,7 +312,7 @@ class StatementInterpreter implements o.StatementVisitor, o.ExpressionVisitor {
|
|||||||
return expressions.map((expr) => expr.visitExpression(this, ctx));
|
return expressions.map((expr) => expr.visitExpression(this, ctx));
|
||||||
}
|
}
|
||||||
|
|
||||||
visitAllStatements(statements: o.Statement[], ctx: _ExecutionContext): ReturnValue {
|
visitAllStatements(statements: o.Statement[], ctx: _ExecutionContext): ReturnValue|null {
|
||||||
for (let i = 0; i < statements.length; i++) {
|
for (let i = 0; i < statements.length; i++) {
|
||||||
const stmt = statements[i];
|
const stmt = statements[i];
|
||||||
const val = stmt.visitStatement(this, ctx);
|
const val = stmt.visitStatement(this, ctx);
|
||||||
|
@ -16,17 +16,16 @@ export abstract class ImportResolver {
|
|||||||
* Converts a file path to a module name that can be used as an `import.
|
* Converts a file path to a module name that can be used as an `import.
|
||||||
* I.e. `path/to/importedFile.ts` should be imported by `path/to/containingFile.ts`.
|
* I.e. `path/to/importedFile.ts` should be imported by `path/to/containingFile.ts`.
|
||||||
*/
|
*/
|
||||||
abstract fileNameToModuleName(importedFilePath: string, containingFilePath: string): string
|
abstract fileNameToModuleName(importedFilePath: string, containingFilePath: string): string|null;
|
||||||
/*|null*/;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Converts the given StaticSymbol into another StaticSymbol that should be used
|
* Converts the given StaticSymbol into another StaticSymbol that should be used
|
||||||
* to generate the import from.
|
* to generate the import from.
|
||||||
*/
|
*/
|
||||||
abstract getImportAs(symbol: StaticSymbol): StaticSymbol /*|null*/;
|
abstract getImportAs(symbol: StaticSymbol): StaticSymbol|null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Determine the arity of a type.
|
* Determine the arity of a type.
|
||||||
*/
|
*/
|
||||||
abstract getTypeArity(symbol: StaticSymbol): number /*|null*/;
|
abstract getTypeArity(symbol: StaticSymbol): number|null;
|
||||||
}
|
}
|
||||||
|
@ -25,12 +25,12 @@ export type SourceMap = {
|
|||||||
file?: string,
|
file?: string,
|
||||||
sourceRoot: string,
|
sourceRoot: string,
|
||||||
sources: string[],
|
sources: string[],
|
||||||
sourcesContent: string[],
|
sourcesContent: (string | null)[],
|
||||||
mappings: string,
|
mappings: string,
|
||||||
};
|
};
|
||||||
|
|
||||||
export class SourceMapGenerator {
|
export class SourceMapGenerator {
|
||||||
private sourcesContent: Map<string, string> = new Map();
|
private sourcesContent: Map<string, string|null> = new Map();
|
||||||
private lines: Segment[][] = [];
|
private lines: Segment[][] = [];
|
||||||
private lastCol0: number = 0;
|
private lastCol0: number = 0;
|
||||||
private hasMappings = false;
|
private hasMappings = false;
|
||||||
@ -83,7 +83,7 @@ export class SourceMapGenerator {
|
|||||||
|
|
||||||
const sourcesIndex = new Map<string, number>();
|
const sourcesIndex = new Map<string, number>();
|
||||||
const sources: string[] = [];
|
const sources: string[] = [];
|
||||||
const sourcesContent: string[] = [];
|
const sourcesContent: (string | null)[] = [];
|
||||||
|
|
||||||
Array.from(this.sourcesContent.keys()).forEach((url: string, i: number) => {
|
Array.from(this.sourcesContent.keys()).forEach((url: string, i: number) => {
|
||||||
sourcesIndex.set(url, i);
|
sourcesIndex.set(url, i);
|
||||||
@ -109,14 +109,14 @@ export class SourceMapGenerator {
|
|||||||
if (segment.sourceUrl != null) {
|
if (segment.sourceUrl != null) {
|
||||||
// zero-based index into the “sources” list
|
// zero-based index into the “sources” list
|
||||||
segAsStr +=
|
segAsStr +=
|
||||||
toBase64VLQ(sourcesIndex.get(segment.sourceUrl) - lastSourceIndex);
|
toBase64VLQ(sourcesIndex.get(segment.sourceUrl) ! - lastSourceIndex);
|
||||||
lastSourceIndex = sourcesIndex.get(segment.sourceUrl);
|
lastSourceIndex = sourcesIndex.get(segment.sourceUrl) !;
|
||||||
// the zero-based starting line in the original source
|
// the zero-based starting line in the original source
|
||||||
segAsStr += toBase64VLQ(segment.sourceLine0 - lastSourceLine0);
|
segAsStr += toBase64VLQ(segment.sourceLine0 ! - lastSourceLine0);
|
||||||
lastSourceLine0 = segment.sourceLine0;
|
lastSourceLine0 = segment.sourceLine0 !;
|
||||||
// the zero-based starting column in the original source
|
// the zero-based starting column in the original source
|
||||||
segAsStr += toBase64VLQ(segment.sourceCol0 - lastSourceCol0);
|
segAsStr += toBase64VLQ(segment.sourceCol0 ! - lastSourceCol0);
|
||||||
lastSourceCol0 = segment.sourceCol0;
|
lastSourceCol0 = segment.sourceCol0 !;
|
||||||
}
|
}
|
||||||
|
|
||||||
return segAsStr;
|
return segAsStr;
|
||||||
|
@ -20,7 +20,7 @@ export function debugOutputAstAsTypeScript(ast: o.Statement | o.Expression | o.T
|
|||||||
string {
|
string {
|
||||||
const converter = new _TsEmitterVisitor(_debugFilePath, {
|
const converter = new _TsEmitterVisitor(_debugFilePath, {
|
||||||
fileNameToModuleName(filePath: string, containingFilePath: string) { return filePath; },
|
fileNameToModuleName(filePath: string, containingFilePath: string) { return filePath; },
|
||||||
getImportAs(symbol: StaticSymbol) { return null; },
|
getImportAs(symbol: StaticSymbol | null) { return null; },
|
||||||
getTypeArity: symbol => null
|
getTypeArity: symbol => null
|
||||||
});
|
});
|
||||||
const ctx = EmitterVisitorContext.createRoot([]);
|
const ctx = EmitterVisitorContext.createRoot([]);
|
||||||
@ -89,8 +89,8 @@ class _TsEmitterVisitor extends AbstractEmitterVisitor implements o.TypeVisitor
|
|||||||
importsWithPrefixes = new Map<string, string>();
|
importsWithPrefixes = new Map<string, string>();
|
||||||
reexports = new Map<string, {name: string, as: string}[]>();
|
reexports = new Map<string, {name: string, as: string}[]>();
|
||||||
|
|
||||||
visitType(t: o.Type, ctx: EmitterVisitorContext, defaultType: string = 'any') {
|
visitType(t: o.Type|null, ctx: EmitterVisitorContext, defaultType: string = 'any') {
|
||||||
if (t != null) {
|
if (t) {
|
||||||
this.typeExpression++;
|
this.typeExpression++;
|
||||||
t.visitType(this, ctx);
|
t.visitType(this, ctx);
|
||||||
this.typeExpression--;
|
this.typeExpression--;
|
||||||
@ -133,7 +133,7 @@ class _TsEmitterVisitor extends AbstractEmitterVisitor implements o.TypeVisitor
|
|||||||
if (ctx.isExportedVar(stmt.name) && stmt.value instanceof o.ExternalExpr && !stmt.type) {
|
if (ctx.isExportedVar(stmt.name) && stmt.value instanceof o.ExternalExpr && !stmt.type) {
|
||||||
// check for a reexport
|
// check for a reexport
|
||||||
const {name, filePath, members} = this._resolveStaticSymbol(stmt.value.value);
|
const {name, filePath, members} = this._resolveStaticSymbol(stmt.value.value);
|
||||||
if (members.length === 0 && filePath !== this._genFilePath) {
|
if (members !.length === 0 && filePath !== this._genFilePath) {
|
||||||
let reexports = this.reexports.get(filePath);
|
let reexports = this.reexports.get(filePath);
|
||||||
if (!reexports) {
|
if (!reexports) {
|
||||||
reexports = [];
|
reexports = [];
|
||||||
@ -161,7 +161,7 @@ class _TsEmitterVisitor extends AbstractEmitterVisitor implements o.TypeVisitor
|
|||||||
|
|
||||||
visitCastExpr(ast: o.CastExpr, ctx: EmitterVisitorContext): any {
|
visitCastExpr(ast: o.CastExpr, ctx: EmitterVisitorContext): any {
|
||||||
ctx.print(ast, `(<`);
|
ctx.print(ast, `(<`);
|
||||||
ast.type.visitType(this, ctx);
|
ast.type !.visitType(this, ctx);
|
||||||
ctx.print(ast, `>`);
|
ctx.print(ast, `>`);
|
||||||
ast.value.visitExpression(this, ctx);
|
ast.value.visitExpression(this, ctx);
|
||||||
ctx.print(ast, `)`);
|
ctx.print(ast, `)`);
|
||||||
@ -290,7 +290,7 @@ class _TsEmitterVisitor extends AbstractEmitterVisitor implements o.TypeVisitor
|
|||||||
ctx.println(stmt, `} catch (${CATCH_ERROR_VAR.name}) {`);
|
ctx.println(stmt, `} catch (${CATCH_ERROR_VAR.name}) {`);
|
||||||
ctx.incIndent();
|
ctx.incIndent();
|
||||||
const catchStmts =
|
const catchStmts =
|
||||||
[<o.Statement>CATCH_STACK_VAR.set(CATCH_ERROR_VAR.prop('stack')).toDeclStmt(null, [
|
[<o.Statement>CATCH_STACK_VAR.set(CATCH_ERROR_VAR.prop('stack', null)).toDeclStmt(null, [
|
||||||
o.StmtModifier.Final
|
o.StmtModifier.Final
|
||||||
])].concat(stmt.catchStmts);
|
])].concat(stmt.catchStmts);
|
||||||
this.visitAllStatements(catchStmts, ctx);
|
this.visitAllStatements(catchStmts, ctx);
|
||||||
@ -386,7 +386,8 @@ class _TsEmitterVisitor extends AbstractEmitterVisitor implements o.TypeVisitor
|
|||||||
}
|
}
|
||||||
|
|
||||||
private _visitIdentifier(
|
private _visitIdentifier(
|
||||||
value: CompileIdentifierMetadata, typeParams: o.Type[], ctx: EmitterVisitorContext): void {
|
value: CompileIdentifierMetadata, typeParams: o.Type[]|null,
|
||||||
|
ctx: EmitterVisitorContext): void {
|
||||||
const {name, filePath, members, arity} = this._resolveStaticSymbol(value);
|
const {name, filePath, members, arity} = this._resolveStaticSymbol(value);
|
||||||
if (filePath != this._genFilePath) {
|
if (filePath != this._genFilePath) {
|
||||||
let prefix = this.importsWithPrefixes.get(filePath);
|
let prefix = this.importsWithPrefixes.get(filePath);
|
||||||
@ -396,10 +397,10 @@ class _TsEmitterVisitor extends AbstractEmitterVisitor implements o.TypeVisitor
|
|||||||
}
|
}
|
||||||
ctx.print(null, `${prefix}.`);
|
ctx.print(null, `${prefix}.`);
|
||||||
}
|
}
|
||||||
if (members.length) {
|
if (members !.length) {
|
||||||
ctx.print(null, name);
|
ctx.print(null, name);
|
||||||
ctx.print(null, '.');
|
ctx.print(null, '.');
|
||||||
ctx.print(null, members.join('.'));
|
ctx.print(null, members !.join('.'));
|
||||||
} else {
|
} else {
|
||||||
ctx.print(null, name);
|
ctx.print(null, name);
|
||||||
}
|
}
|
||||||
@ -415,7 +416,7 @@ class _TsEmitterVisitor extends AbstractEmitterVisitor implements o.TypeVisitor
|
|||||||
if (suppliedParameters > 0 || additionalParameters > 0) {
|
if (suppliedParameters > 0 || additionalParameters > 0) {
|
||||||
ctx.print(null, `<`);
|
ctx.print(null, `<`);
|
||||||
if (suppliedParameters > 0) {
|
if (suppliedParameters > 0) {
|
||||||
this.visitAllObjects(type => type.visitType(this, ctx), typeParams, ctx, ',');
|
this.visitAllObjects(type => type.visitType(this, ctx), typeParams !, ctx, ',');
|
||||||
}
|
}
|
||||||
if (additionalParameters > 0) {
|
if (additionalParameters > 0) {
|
||||||
for (let i = 0; i < additionalParameters; i++) {
|
for (let i = 0; i < additionalParameters; i++) {
|
||||||
@ -428,7 +429,7 @@ class _TsEmitterVisitor extends AbstractEmitterVisitor implements o.TypeVisitor
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private _printColonType(type: o.Type, ctx: EmitterVisitorContext, defaultType?: string) {
|
private _printColonType(type: o.Type|null, ctx: EmitterVisitorContext, defaultType?: string) {
|
||||||
if (type !== o.INFERRED_TYPE) {
|
if (type !== o.INFERRED_TYPE) {
|
||||||
ctx.print(null, ':');
|
ctx.print(null, ':');
|
||||||
this.visitType(type, ctx, defaultType);
|
this.visitType(type, ctx, defaultType);
|
||||||
|
@ -13,7 +13,7 @@ import * as o from './output_ast';
|
|||||||
|
|
||||||
export const QUOTED_KEYS = '$quoted$';
|
export const QUOTED_KEYS = '$quoted$';
|
||||||
|
|
||||||
export function convertValueToOutputAst(value: any, type: o.Type = null): o.Expression {
|
export function convertValueToOutputAst(value: any, type: o.Type | null = null): o.Expression {
|
||||||
return visitValue(value, new _ValueOutputAstTransformer(), type);
|
return visitValue(value, new _ValueOutputAstTransformer(), type);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -51,7 +51,7 @@ export class ParseLocation {
|
|||||||
|
|
||||||
// Return the source around the location
|
// Return the source around the location
|
||||||
// Up to `maxChars` or `maxLines` on each side of the location
|
// Up to `maxChars` or `maxLines` on each side of the location
|
||||||
getContext(maxChars: number, maxLines: number): {before: string, after: string} {
|
getContext(maxChars: number, maxLines: number): {before: string, after: string}|null {
|
||||||
const content = this.file.content;
|
const content = this.file.content;
|
||||||
let startOffset = this.offset;
|
let startOffset = this.offset;
|
||||||
|
|
||||||
@ -101,7 +101,7 @@ export class ParseSourceFile {
|
|||||||
|
|
||||||
export class ParseSourceSpan {
|
export class ParseSourceSpan {
|
||||||
constructor(
|
constructor(
|
||||||
public start: ParseLocation, public end: ParseLocation, public details: string = null) {}
|
public start: ParseLocation, public end: ParseLocation, public details: string|null = null) {}
|
||||||
|
|
||||||
toString(): string {
|
toString(): string {
|
||||||
return this.start.file.content.substring(this.start.offset, this.end.offset);
|
return this.start.file.content.substring(this.start.offset, this.end.offset);
|
||||||
@ -133,6 +133,5 @@ export function typeSourceSpan(kind: string, type: CompileIdentifierMetadata): P
|
|||||||
`in ${kind} ${identifierName(type)}`;
|
`in ${kind} ${identifierName(type)}`;
|
||||||
const sourceFile = new ParseSourceFile('', sourceFileName);
|
const sourceFile = new ParseSourceFile('', sourceFileName);
|
||||||
return new ParseSourceSpan(
|
return new ParseSourceSpan(
|
||||||
new ParseLocation(sourceFile, null, null, null),
|
new ParseLocation(sourceFile, -1, -1, -1), new ParseLocation(sourceFile, -1, -1, -1));
|
||||||
new ParseLocation(sourceFile, null, null, null));
|
|
||||||
}
|
}
|
||||||
|
@ -33,7 +33,7 @@ export class PipeResolver {
|
|||||||
/**
|
/**
|
||||||
* Return {@link Pipe} for a given `Type`.
|
* Return {@link Pipe} for a given `Type`.
|
||||||
*/
|
*/
|
||||||
resolve(type: Type<any>, throwIfNotFound = true): Pipe {
|
resolve(type: Type<any>, throwIfNotFound = true): Pipe|null {
|
||||||
const metas = this._reflector.annotations(resolveForwardRef(type));
|
const metas = this._reflector.annotations(resolveForwardRef(type));
|
||||||
if (metas) {
|
if (metas) {
|
||||||
const annotation = findLast(metas, _isPipeMetadata);
|
const annotation = findLast(metas, _isPipeMetadata);
|
||||||
|
@ -135,7 +135,7 @@ export class ProviderElementContext {
|
|||||||
const result: QueryWithId[] = [];
|
const result: QueryWithId[] = [];
|
||||||
let currentEl: ProviderElementContext = this;
|
let currentEl: ProviderElementContext = this;
|
||||||
let distance = 0;
|
let distance = 0;
|
||||||
let queries: QueryWithId[];
|
let queries: QueryWithId[]|undefined;
|
||||||
while (currentEl !== null) {
|
while (currentEl !== null) {
|
||||||
queries = currentEl._contentQueries.get(tokenReference(token));
|
queries = currentEl._contentQueries.get(tokenReference(token));
|
||||||
if (queries) {
|
if (queries) {
|
||||||
@ -156,7 +156,7 @@ export class ProviderElementContext {
|
|||||||
|
|
||||||
private _getOrCreateLocalProvider(
|
private _getOrCreateLocalProvider(
|
||||||
requestingProviderType: ProviderAstType, token: CompileTokenMetadata,
|
requestingProviderType: ProviderAstType, token: CompileTokenMetadata,
|
||||||
eager: boolean): ProviderAst {
|
eager: boolean): ProviderAst|null {
|
||||||
const resolvedProvider = this._allProviders.get(tokenReference(token));
|
const resolvedProvider = this._allProviders.get(tokenReference(token));
|
||||||
if (!resolvedProvider || ((requestingProviderType === ProviderAstType.Directive ||
|
if (!resolvedProvider || ((requestingProviderType === ProviderAstType.Directive ||
|
||||||
requestingProviderType === ProviderAstType.PublicService) &&
|
requestingProviderType === ProviderAstType.PublicService) &&
|
||||||
@ -178,25 +178,25 @@ export class ProviderElementContext {
|
|||||||
this._seenProviders.set(tokenReference(token), true);
|
this._seenProviders.set(tokenReference(token), true);
|
||||||
const transformedProviders = resolvedProvider.providers.map((provider) => {
|
const transformedProviders = resolvedProvider.providers.map((provider) => {
|
||||||
let transformedUseValue = provider.useValue;
|
let transformedUseValue = provider.useValue;
|
||||||
let transformedUseExisting = provider.useExisting;
|
let transformedUseExisting = provider.useExisting !;
|
||||||
let transformedDeps: CompileDiDependencyMetadata[];
|
let transformedDeps: CompileDiDependencyMetadata[] = undefined !;
|
||||||
if (provider.useExisting != null) {
|
if (provider.useExisting != null) {
|
||||||
const existingDiDep = this._getDependency(
|
const existingDiDep = this._getDependency(
|
||||||
resolvedProvider.providerType, {token: provider.useExisting}, eager);
|
resolvedProvider.providerType, {token: provider.useExisting}, eager) !;
|
||||||
if (existingDiDep.token != null) {
|
if (existingDiDep.token != null) {
|
||||||
transformedUseExisting = existingDiDep.token;
|
transformedUseExisting = existingDiDep.token;
|
||||||
} else {
|
} else {
|
||||||
transformedUseExisting = null;
|
transformedUseExisting = null !;
|
||||||
transformedUseValue = existingDiDep.value;
|
transformedUseValue = existingDiDep.value;
|
||||||
}
|
}
|
||||||
} else if (provider.useFactory) {
|
} else if (provider.useFactory) {
|
||||||
const deps = provider.deps || provider.useFactory.diDeps;
|
const deps = provider.deps || provider.useFactory.diDeps;
|
||||||
transformedDeps =
|
transformedDeps =
|
||||||
deps.map((dep) => this._getDependency(resolvedProvider.providerType, dep, eager));
|
deps.map((dep) => this._getDependency(resolvedProvider.providerType, dep, eager) !);
|
||||||
} else if (provider.useClass) {
|
} else if (provider.useClass) {
|
||||||
const deps = provider.deps || provider.useClass.diDeps;
|
const deps = provider.deps || provider.useClass.diDeps;
|
||||||
transformedDeps =
|
transformedDeps =
|
||||||
deps.map((dep) => this._getDependency(resolvedProvider.providerType, dep, eager));
|
deps.map((dep) => this._getDependency(resolvedProvider.providerType, dep, eager) !);
|
||||||
}
|
}
|
||||||
return _transformProvider(provider, {
|
return _transformProvider(provider, {
|
||||||
useExisting: transformedUseExisting,
|
useExisting: transformedUseExisting,
|
||||||
@ -212,9 +212,9 @@ export class ProviderElementContext {
|
|||||||
|
|
||||||
private _getLocalDependency(
|
private _getLocalDependency(
|
||||||
requestingProviderType: ProviderAstType, dep: CompileDiDependencyMetadata,
|
requestingProviderType: ProviderAstType, dep: CompileDiDependencyMetadata,
|
||||||
eager: boolean = null): CompileDiDependencyMetadata {
|
eager: boolean = false): CompileDiDependencyMetadata|null {
|
||||||
if (dep.isAttribute) {
|
if (dep.isAttribute) {
|
||||||
const attrValue = this._attrs[dep.token.value];
|
const attrValue = this._attrs[dep.token !.value];
|
||||||
return {isValue: true, value: attrValue == null ? null : attrValue};
|
return {isValue: true, value: attrValue == null ? null : attrValue};
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -246,10 +246,10 @@ export class ProviderElementContext {
|
|||||||
|
|
||||||
private _getDependency(
|
private _getDependency(
|
||||||
requestingProviderType: ProviderAstType, dep: CompileDiDependencyMetadata,
|
requestingProviderType: ProviderAstType, dep: CompileDiDependencyMetadata,
|
||||||
eager: boolean = null): CompileDiDependencyMetadata {
|
eager: boolean = false): CompileDiDependencyMetadata|null {
|
||||||
let currElement: ProviderElementContext = this;
|
let currElement: ProviderElementContext = this;
|
||||||
let currEager: boolean = eager;
|
let currEager: boolean = eager;
|
||||||
let result: CompileDiDependencyMetadata = null;
|
let result: CompileDiDependencyMetadata|null = null;
|
||||||
if (!dep.isSkipSelf) {
|
if (!dep.isSkipSelf) {
|
||||||
result = this._getLocalDependency(requestingProviderType, dep, eager);
|
result = this._getLocalDependency(requestingProviderType, dep, eager);
|
||||||
}
|
}
|
||||||
@ -270,8 +270,8 @@ export class ProviderElementContext {
|
|||||||
// check @Host restriction
|
// check @Host restriction
|
||||||
if (!result) {
|
if (!result) {
|
||||||
if (!dep.isHost || this.viewContext.component.isHost ||
|
if (!dep.isHost || this.viewContext.component.isHost ||
|
||||||
this.viewContext.component.type.reference === tokenReference(dep.token) ||
|
this.viewContext.component.type.reference === tokenReference(dep.token !) ||
|
||||||
this.viewContext.viewProviders.get(tokenReference(dep.token)) != null) {
|
this.viewContext.viewProviders.get(tokenReference(dep.token !)) != null) {
|
||||||
result = dep;
|
result = dep;
|
||||||
} else {
|
} else {
|
||||||
result = dep.isOptional ? result = {isValue: true, value: null} : null;
|
result = dep.isOptional ? result = {isValue: true, value: null} : null;
|
||||||
@ -280,7 +280,7 @@ export class ProviderElementContext {
|
|||||||
}
|
}
|
||||||
if (!result) {
|
if (!result) {
|
||||||
this.viewContext.errors.push(
|
this.viewContext.errors.push(
|
||||||
new ProviderError(`No provider for ${tokenName(dep.token)}`, this._sourceSpan));
|
new ProviderError(`No provider for ${tokenName(dep.token!)}`, this._sourceSpan));
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@ -319,7 +319,7 @@ export class NgModuleProviderAnalyzer {
|
|||||||
return Array.from(this._transformedProviders.values());
|
return Array.from(this._transformedProviders.values());
|
||||||
}
|
}
|
||||||
|
|
||||||
private _getOrCreateLocalProvider(token: CompileTokenMetadata, eager: boolean): ProviderAst {
|
private _getOrCreateLocalProvider(token: CompileTokenMetadata, eager: boolean): ProviderAst|null {
|
||||||
const resolvedProvider = this._allProviders.get(tokenReference(token));
|
const resolvedProvider = this._allProviders.get(tokenReference(token));
|
||||||
if (!resolvedProvider) {
|
if (!resolvedProvider) {
|
||||||
return null;
|
return null;
|
||||||
@ -337,15 +337,15 @@ export class NgModuleProviderAnalyzer {
|
|||||||
this._seenProviders.set(tokenReference(token), true);
|
this._seenProviders.set(tokenReference(token), true);
|
||||||
const transformedProviders = resolvedProvider.providers.map((provider) => {
|
const transformedProviders = resolvedProvider.providers.map((provider) => {
|
||||||
let transformedUseValue = provider.useValue;
|
let transformedUseValue = provider.useValue;
|
||||||
let transformedUseExisting = provider.useExisting;
|
let transformedUseExisting = provider.useExisting !;
|
||||||
let transformedDeps: CompileDiDependencyMetadata[];
|
let transformedDeps: CompileDiDependencyMetadata[] = undefined !;
|
||||||
if (provider.useExisting != null) {
|
if (provider.useExisting != null) {
|
||||||
const existingDiDep =
|
const existingDiDep =
|
||||||
this._getDependency({token: provider.useExisting}, eager, resolvedProvider.sourceSpan);
|
this._getDependency({token: provider.useExisting}, eager, resolvedProvider.sourceSpan);
|
||||||
if (existingDiDep.token != null) {
|
if (existingDiDep.token != null) {
|
||||||
transformedUseExisting = existingDiDep.token;
|
transformedUseExisting = existingDiDep.token;
|
||||||
} else {
|
} else {
|
||||||
transformedUseExisting = null;
|
transformedUseExisting = null !;
|
||||||
transformedUseValue = existingDiDep.value;
|
transformedUseValue = existingDiDep.value;
|
||||||
}
|
}
|
||||||
} else if (provider.useFactory) {
|
} else if (provider.useFactory) {
|
||||||
@ -370,7 +370,7 @@ export class NgModuleProviderAnalyzer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private _getDependency(
|
private _getDependency(
|
||||||
dep: CompileDiDependencyMetadata, eager: boolean = null,
|
dep: CompileDiDependencyMetadata, eager: boolean = false,
|
||||||
requestorSourceSpan: ParseSourceSpan): CompileDiDependencyMetadata {
|
requestorSourceSpan: ParseSourceSpan): CompileDiDependencyMetadata {
|
||||||
let foundLocal = false;
|
let foundLocal = false;
|
||||||
if (!dep.isSkipSelf && dep.token != null) {
|
if (!dep.isSkipSelf && dep.token != null) {
|
||||||
@ -389,7 +389,7 @@ export class NgModuleProviderAnalyzer {
|
|||||||
result = {isValue: true, value: null};
|
result = {isValue: true, value: null};
|
||||||
} else {
|
} else {
|
||||||
this._errors.push(
|
this._errors.push(
|
||||||
new ProviderError(`No provider for ${tokenName(dep.token)}`, requestorSourceSpan));
|
new ProviderError(`No provider for ${tokenName(dep.token!)}`, requestorSourceSpan));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
@ -464,7 +464,7 @@ function _resolveProviders(
|
|||||||
[];
|
[];
|
||||||
const isUseValue = !(provider.useClass || provider.useExisting || provider.useFactory);
|
const isUseValue = !(provider.useClass || provider.useExisting || provider.useFactory);
|
||||||
resolvedProvider = new ProviderAst(
|
resolvedProvider = new ProviderAst(
|
||||||
provider.token, provider.multi, eager || isUseValue, [provider], providerType,
|
provider.token, !!provider.multi, eager || isUseValue, [provider], providerType,
|
||||||
lifecycleHooks, sourceSpan);
|
lifecycleHooks, sourceSpan);
|
||||||
targetProvidersByToken.set(tokenReference(provider.token), resolvedProvider);
|
targetProvidersByToken.set(tokenReference(provider.token), resolvedProvider);
|
||||||
} else {
|
} else {
|
||||||
|
@ -11,5 +11,5 @@
|
|||||||
* to load templates.
|
* to load templates.
|
||||||
*/
|
*/
|
||||||
export class ResourceLoader {
|
export class ResourceLoader {
|
||||||
get(url: string): Promise<string> { return null; }
|
get(url: string): Promise<string>|null { return null; }
|
||||||
}
|
}
|
||||||
|
@ -386,7 +386,7 @@ export class DomElementSchemaRegistry extends ElementSchemaRegistry {
|
|||||||
{error: string, value: string} {
|
{error: string, value: string} {
|
||||||
let unit: string = '';
|
let unit: string = '';
|
||||||
const strVal = val.toString().trim();
|
const strVal = val.toString().trim();
|
||||||
let errorMsg: string = null;
|
let errorMsg: string = null !;
|
||||||
|
|
||||||
if (_isPixelDimensionStyle(camelCaseProp) && val !== 0 && val !== '0') {
|
if (_isPixelDimensionStyle(camelCaseProp) && val !== 0 && val !== '0') {
|
||||||
if (typeof val === 'number') {
|
if (typeof val === 'number') {
|
||||||
|
@ -26,7 +26,7 @@ const _SELECTOR_REGEXP = new RegExp(
|
|||||||
* of selecting subsets out of them.
|
* of selecting subsets out of them.
|
||||||
*/
|
*/
|
||||||
export class CssSelector {
|
export class CssSelector {
|
||||||
element: string = null;
|
element: string|null = null;
|
||||||
classNames: string[] = [];
|
classNames: string[] = [];
|
||||||
attrs: string[] = [];
|
attrs: string[] = [];
|
||||||
notSelectors: CssSelector[] = [];
|
notSelectors: CssSelector[] = [];
|
||||||
@ -41,7 +41,7 @@ export class CssSelector {
|
|||||||
res.push(cssSel);
|
res.push(cssSel);
|
||||||
};
|
};
|
||||||
let cssSelector = new CssSelector();
|
let cssSelector = new CssSelector();
|
||||||
let match: string[];
|
let match: string[]|null;
|
||||||
let current = cssSelector;
|
let current = cssSelector;
|
||||||
let inNot = false;
|
let inNot = false;
|
||||||
_SELECTOR_REGEXP.lastIndex = 0;
|
_SELECTOR_REGEXP.lastIndex = 0;
|
||||||
@ -86,7 +86,7 @@ export class CssSelector {
|
|||||||
|
|
||||||
hasElementSelector(): boolean { return !!this.element; }
|
hasElementSelector(): boolean { return !!this.element; }
|
||||||
|
|
||||||
setElement(element: string = null) { this.element = element; }
|
setElement(element: string|null = null) { this.element = element; }
|
||||||
|
|
||||||
/** Gets a template string for an element that matches the selector. */
|
/** Gets a template string for an element that matches the selector. */
|
||||||
getMatchingElementTemplate(): string {
|
getMatchingElementTemplate(): string {
|
||||||
@ -147,7 +147,7 @@ export class SelectorMatcher {
|
|||||||
private _listContexts: SelectorListContext[] = [];
|
private _listContexts: SelectorListContext[] = [];
|
||||||
|
|
||||||
addSelectables(cssSelectors: CssSelector[], callbackCtxt?: any) {
|
addSelectables(cssSelectors: CssSelector[], callbackCtxt?: any) {
|
||||||
let listContext: SelectorListContext = null;
|
let listContext: SelectorListContext = null !;
|
||||||
if (cssSelectors.length > 1) {
|
if (cssSelectors.length > 1) {
|
||||||
listContext = new SelectorListContext(cssSelectors);
|
listContext = new SelectorListContext(cssSelectors);
|
||||||
this._listContexts.push(listContext);
|
this._listContexts.push(listContext);
|
||||||
@ -243,9 +243,10 @@ export class SelectorMatcher {
|
|||||||
* @param matchedCallback This callback will be called with the object handed into `addSelectable`
|
* @param matchedCallback This callback will be called with the object handed into `addSelectable`
|
||||||
* @return boolean true if a match was found
|
* @return boolean true if a match was found
|
||||||
*/
|
*/
|
||||||
match(cssSelector: CssSelector, matchedCallback: (c: CssSelector, a: any) => void): boolean {
|
match(cssSelector: CssSelector, matchedCallback: ((c: CssSelector, a: any) => void)|null):
|
||||||
|
boolean {
|
||||||
let result = false;
|
let result = false;
|
||||||
const element = cssSelector.element;
|
const element = cssSelector.element !;
|
||||||
const classNames = cssSelector.classNames;
|
const classNames = cssSelector.classNames;
|
||||||
const attrs = cssSelector.attrs;
|
const attrs = cssSelector.attrs;
|
||||||
|
|
||||||
@ -273,7 +274,7 @@ export class SelectorMatcher {
|
|||||||
const name = attrs[i];
|
const name = attrs[i];
|
||||||
const value = attrs[i + 1];
|
const value = attrs[i + 1];
|
||||||
|
|
||||||
const terminalValuesMap = this._attrValueMap.get(name);
|
const terminalValuesMap = this._attrValueMap.get(name) !;
|
||||||
if (value) {
|
if (value) {
|
||||||
result =
|
result =
|
||||||
this._matchTerminal(terminalValuesMap, '', cssSelector, matchedCallback) || result;
|
this._matchTerminal(terminalValuesMap, '', cssSelector, matchedCallback) || result;
|
||||||
@ -281,7 +282,7 @@ export class SelectorMatcher {
|
|||||||
result =
|
result =
|
||||||
this._matchTerminal(terminalValuesMap, value, cssSelector, matchedCallback) || result;
|
this._matchTerminal(terminalValuesMap, value, cssSelector, matchedCallback) || result;
|
||||||
|
|
||||||
const partialValuesMap = this._attrValuePartialMap.get(name);
|
const partialValuesMap = this._attrValuePartialMap.get(name) !;
|
||||||
if (value) {
|
if (value) {
|
||||||
result = this._matchPartial(partialValuesMap, '', cssSelector, matchedCallback) || result;
|
result = this._matchPartial(partialValuesMap, '', cssSelector, matchedCallback) || result;
|
||||||
}
|
}
|
||||||
@ -295,13 +296,13 @@ export class SelectorMatcher {
|
|||||||
/** @internal */
|
/** @internal */
|
||||||
_matchTerminal(
|
_matchTerminal(
|
||||||
map: Map<string, SelectorContext[]>, name: string, cssSelector: CssSelector,
|
map: Map<string, SelectorContext[]>, name: string, cssSelector: CssSelector,
|
||||||
matchedCallback: (c: CssSelector, a: any) => void): boolean {
|
matchedCallback: ((c: CssSelector, a: any) => void)|null): boolean {
|
||||||
if (!map || typeof name !== 'string') {
|
if (!map || typeof name !== 'string') {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
let selectables: SelectorContext[] = map.get(name) || [];
|
let selectables: SelectorContext[] = map.get(name) || [];
|
||||||
const starSelectables: SelectorContext[] = map.get('*');
|
const starSelectables: SelectorContext[] = map.get('*') !;
|
||||||
if (starSelectables) {
|
if (starSelectables) {
|
||||||
selectables = selectables.concat(starSelectables);
|
selectables = selectables.concat(starSelectables);
|
||||||
}
|
}
|
||||||
@ -320,7 +321,7 @@ export class SelectorMatcher {
|
|||||||
/** @internal */
|
/** @internal */
|
||||||
_matchPartial(
|
_matchPartial(
|
||||||
map: Map<string, SelectorMatcher>, name: string, cssSelector: CssSelector,
|
map: Map<string, SelectorMatcher>, name: string, cssSelector: CssSelector,
|
||||||
matchedCallback: (c: CssSelector, a: any) => void): boolean {
|
matchedCallback: ((c: CssSelector, a: any) => void)|null): boolean {
|
||||||
if (!map || typeof name !== 'string') {
|
if (!map || typeof name !== 'string') {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -353,7 +354,7 @@ export class SelectorContext {
|
|||||||
this.notSelectors = selector.notSelectors;
|
this.notSelectors = selector.notSelectors;
|
||||||
}
|
}
|
||||||
|
|
||||||
finalize(cssSelector: CssSelector, callback: (c: CssSelector, a: any) => void): boolean {
|
finalize(cssSelector: CssSelector, callback: ((c: CssSelector, a: any) => void)|null): boolean {
|
||||||
let result = true;
|
let result = true;
|
||||||
if (this.notSelectors.length > 0 && (!this.listContext || !this.listContext.alreadyMatched)) {
|
if (this.notSelectors.length > 0 && (!this.listContext || !this.listContext.alreadyMatched)) {
|
||||||
const notMatcher = SelectorMatcher.createNotMatcher(this.notSelectors);
|
const notMatcher = SelectorMatcher.createNotMatcher(this.notSelectors);
|
||||||
|
@ -240,7 +240,7 @@ export class ShadowCss {
|
|||||||
private _extractUnscopedRulesFromCssText(cssText: string): string {
|
private _extractUnscopedRulesFromCssText(cssText: string): string {
|
||||||
// Difference with webcomponents.js: does not handle comments
|
// Difference with webcomponents.js: does not handle comments
|
||||||
let r = '';
|
let r = '';
|
||||||
let m: RegExpExecArray;
|
let m: RegExpExecArray|null;
|
||||||
_cssContentUnscopedRuleRe.lastIndex = 0;
|
_cssContentUnscopedRuleRe.lastIndex = 0;
|
||||||
while ((m = _cssContentUnscopedRuleRe.exec(cssText)) !== null) {
|
while ((m = _cssContentUnscopedRuleRe.exec(cssText)) !== null) {
|
||||||
const rule = m[0].replace(m[2], '').replace(m[1], m[4]);
|
const rule = m[0].replace(m[2], '').replace(m[1], m[4]);
|
||||||
@ -433,7 +433,7 @@ export class ShadowCss {
|
|||||||
|
|
||||||
let scopedSelector = '';
|
let scopedSelector = '';
|
||||||
let startIndex = 0;
|
let startIndex = 0;
|
||||||
let res: RegExpExecArray;
|
let res: RegExpExecArray|null;
|
||||||
const sep = /( |>|\+|~(?!=))\s*/g;
|
const sep = /( |>|\+|~(?!=))\s*/g;
|
||||||
const scopeAfter = selector.indexOf(_polyfillHostNoCombinator);
|
const scopeAfter = selector.indexOf(_polyfillHostNoCombinator);
|
||||||
|
|
||||||
|
@ -44,15 +44,16 @@ export class StyleCompiler {
|
|||||||
constructor(private _urlResolver: UrlResolver) {}
|
constructor(private _urlResolver: UrlResolver) {}
|
||||||
|
|
||||||
compileComponent(comp: CompileDirectiveMetadata): StylesCompileResult {
|
compileComponent(comp: CompileDirectiveMetadata): StylesCompileResult {
|
||||||
|
const template = comp.template !;
|
||||||
const externalStylesheets: CompiledStylesheet[] = [];
|
const externalStylesheets: CompiledStylesheet[] = [];
|
||||||
const componentStylesheet: CompiledStylesheet = this._compileStyles(
|
const componentStylesheet: CompiledStylesheet = this._compileStyles(
|
||||||
comp, new CompileStylesheetMetadata({
|
comp, new CompileStylesheetMetadata({
|
||||||
styles: comp.template.styles,
|
styles: template.styles,
|
||||||
styleUrls: comp.template.styleUrls,
|
styleUrls: template.styleUrls,
|
||||||
moduleUrl: identifierModuleUrl(comp.type)
|
moduleUrl: identifierModuleUrl(comp.type)
|
||||||
}),
|
}),
|
||||||
true);
|
true);
|
||||||
comp.template.externalStylesheets.forEach((stylesheetMeta) => {
|
template.externalStylesheets.forEach((stylesheetMeta) => {
|
||||||
const compiledStylesheet = this._compileStyles(comp, stylesheetMeta, false);
|
const compiledStylesheet = this._compileStyles(comp, stylesheetMeta, false);
|
||||||
externalStylesheets.push(compiledStylesheet);
|
externalStylesheets.push(compiledStylesheet);
|
||||||
});
|
});
|
||||||
@ -62,7 +63,7 @@ export class StyleCompiler {
|
|||||||
private _compileStyles(
|
private _compileStyles(
|
||||||
comp: CompileDirectiveMetadata, stylesheet: CompileStylesheetMetadata,
|
comp: CompileDirectiveMetadata, stylesheet: CompileStylesheetMetadata,
|
||||||
isComponentStylesheet: boolean): CompiledStylesheet {
|
isComponentStylesheet: boolean): CompiledStylesheet {
|
||||||
const shim = comp.template.encapsulation === ViewEncapsulation.Emulated;
|
const shim = comp.template !.encapsulation === ViewEncapsulation.Emulated;
|
||||||
const styleExpressions =
|
const styleExpressions =
|
||||||
stylesheet.styles.map(plainStyle => o.literal(this._shimIfNeeded(plainStyle, shim)));
|
stylesheet.styles.map(plainStyle => o.literal(this._shimIfNeeded(plainStyle, shim)));
|
||||||
const dependencies: StylesCompileDependency[] = [];
|
const dependencies: StylesCompileDependency[] = [];
|
||||||
@ -87,7 +88,7 @@ export class StyleCompiler {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function getStylesVarName(component: CompileDirectiveMetadata): string {
|
function getStylesVarName(component: CompileDirectiveMetadata | null): string {
|
||||||
let result = `styles`;
|
let result = `styles`;
|
||||||
if (component) {
|
if (component) {
|
||||||
result += `_${identifierName(component.type)}`;
|
result += `_${identifierName(component.type)}`;
|
||||||
|
@ -17,8 +17,8 @@ export interface Summary<T> {
|
|||||||
@CompilerInjectable()
|
@CompilerInjectable()
|
||||||
export class SummaryResolver<T> {
|
export class SummaryResolver<T> {
|
||||||
isLibraryFile(fileName: string): boolean { return false; };
|
isLibraryFile(fileName: string): boolean { return false; };
|
||||||
getLibraryFileName(fileName: string): string { return null; }
|
getLibraryFileName(fileName: string): string|null { return null; }
|
||||||
resolveSummary(reference: T): Summary<T> { return null; };
|
resolveSummary(reference: T): Summary<T>|null { return null; };
|
||||||
getSymbolsOf(filePath: string): T[] { return []; }
|
getSymbolsOf(filePath: string): T[] { return []; }
|
||||||
getImportAs(reference: T): T { return reference; }
|
getImportAs(reference: T): T { return reference; }
|
||||||
}
|
}
|
||||||
|
@ -64,7 +64,7 @@ export class BindingParser {
|
|||||||
|
|
||||||
createDirectiveHostPropertyAsts(
|
createDirectiveHostPropertyAsts(
|
||||||
dirMeta: CompileDirectiveSummary, elementSelector: string,
|
dirMeta: CompileDirectiveSummary, elementSelector: string,
|
||||||
sourceSpan: ParseSourceSpan): BoundElementPropertyAst[] {
|
sourceSpan: ParseSourceSpan): BoundElementPropertyAst[]|null {
|
||||||
if (dirMeta.hostProperties) {
|
if (dirMeta.hostProperties) {
|
||||||
const boundProps: BoundProperty[] = [];
|
const boundProps: BoundProperty[] = [];
|
||||||
Object.keys(dirMeta.hostProperties).forEach(propName => {
|
Object.keys(dirMeta.hostProperties).forEach(propName => {
|
||||||
@ -79,10 +79,11 @@ export class BindingParser {
|
|||||||
});
|
});
|
||||||
return boundProps.map((prop) => this.createElementPropertyAst(elementSelector, prop));
|
return boundProps.map((prop) => this.createElementPropertyAst(elementSelector, prop));
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
createDirectiveHostEventAsts(dirMeta: CompileDirectiveSummary, sourceSpan: ParseSourceSpan):
|
createDirectiveHostEventAsts(dirMeta: CompileDirectiveSummary, sourceSpan: ParseSourceSpan):
|
||||||
BoundEventAst[] {
|
BoundEventAst[]|null {
|
||||||
if (dirMeta.hostListeners) {
|
if (dirMeta.hostListeners) {
|
||||||
const targetEventAsts: BoundEventAst[] = [];
|
const targetEventAsts: BoundEventAst[] = [];
|
||||||
Object.keys(dirMeta.hostListeners).forEach(propName => {
|
Object.keys(dirMeta.hostListeners).forEach(propName => {
|
||||||
@ -97,13 +98,15 @@ export class BindingParser {
|
|||||||
});
|
});
|
||||||
return targetEventAsts;
|
return targetEventAsts;
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
parseInterpolation(value: string, sourceSpan: ParseSourceSpan): ASTWithSource {
|
parseInterpolation(value: string, sourceSpan: ParseSourceSpan): ASTWithSource {
|
||||||
const sourceInfo = sourceSpan.start.toString();
|
const sourceInfo = sourceSpan.start.toString();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const ast = this._exprParser.parseInterpolation(value, sourceInfo, this._interpolationConfig);
|
const ast =
|
||||||
|
this._exprParser.parseInterpolation(value, sourceInfo, this._interpolationConfig) !;
|
||||||
if (ast) this._reportExpressionParserErrors(ast.errors, sourceSpan);
|
if (ast) this._reportExpressionParserErrors(ast.errors, sourceSpan);
|
||||||
this._checkPipes(ast, sourceSpan);
|
this._checkPipes(ast, sourceSpan);
|
||||||
return ast;
|
return ast;
|
||||||
@ -153,8 +156,8 @@ export class BindingParser {
|
|||||||
}
|
}
|
||||||
|
|
||||||
parseLiteralAttr(
|
parseLiteralAttr(
|
||||||
name: string, value: string, sourceSpan: ParseSourceSpan, targetMatchableAttrs: string[][],
|
name: string, value: string|null, sourceSpan: ParseSourceSpan,
|
||||||
targetProps: BoundProperty[]) {
|
targetMatchableAttrs: string[][], targetProps: BoundProperty[]) {
|
||||||
if (_isAnimationLabel(name)) {
|
if (_isAnimationLabel(name)) {
|
||||||
name = name.substring(1);
|
name = name.substring(1);
|
||||||
if (value) {
|
if (value) {
|
||||||
@ -206,18 +209,18 @@ export class BindingParser {
|
|||||||
private _parsePropertyAst(
|
private _parsePropertyAst(
|
||||||
name: string, ast: ASTWithSource, sourceSpan: ParseSourceSpan,
|
name: string, ast: ASTWithSource, sourceSpan: ParseSourceSpan,
|
||||||
targetMatchableAttrs: string[][], targetProps: BoundProperty[]) {
|
targetMatchableAttrs: string[][], targetProps: BoundProperty[]) {
|
||||||
targetMatchableAttrs.push([name, ast.source]);
|
targetMatchableAttrs.push([name, ast.source !]);
|
||||||
targetProps.push(new BoundProperty(name, ast, BoundPropertyType.DEFAULT, sourceSpan));
|
targetProps.push(new BoundProperty(name, ast, BoundPropertyType.DEFAULT, sourceSpan));
|
||||||
}
|
}
|
||||||
|
|
||||||
private _parseAnimation(
|
private _parseAnimation(
|
||||||
name: string, expression: string, sourceSpan: ParseSourceSpan,
|
name: string, expression: string|null, sourceSpan: ParseSourceSpan,
|
||||||
targetMatchableAttrs: string[][], targetProps: BoundProperty[]) {
|
targetMatchableAttrs: string[][], targetProps: BoundProperty[]) {
|
||||||
// This will occur when a @trigger is not paired with an expression.
|
// This will occur when a @trigger is not paired with an expression.
|
||||||
// For animations it is valid to not have an expression since */void
|
// For animations it is valid to not have an expression since */void
|
||||||
// states will be applied by angular when the element is attached/detached
|
// states will be applied by angular when the element is attached/detached
|
||||||
const ast = this._parseBinding(expression || 'null', false, sourceSpan);
|
const ast = this._parseBinding(expression || 'null', false, sourceSpan);
|
||||||
targetMatchableAttrs.push([name, ast.source]);
|
targetMatchableAttrs.push([name, ast.source !]);
|
||||||
targetProps.push(new BoundProperty(name, ast, BoundPropertyType.ANIMATION, sourceSpan));
|
targetProps.push(new BoundProperty(name, ast, BoundPropertyType.ANIMATION, sourceSpan));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -246,11 +249,11 @@ export class BindingParser {
|
|||||||
null, boundProp.sourceSpan);
|
null, boundProp.sourceSpan);
|
||||||
}
|
}
|
||||||
|
|
||||||
let unit: string = null;
|
let unit: string|null = null;
|
||||||
let bindingType: PropertyBindingType;
|
let bindingType: PropertyBindingType = undefined !;
|
||||||
let boundPropertyName: string = null;
|
let boundPropertyName: string|null = null;
|
||||||
const parts = boundProp.name.split(PROPERTY_PARTS_SEPARATOR);
|
const parts = boundProp.name.split(PROPERTY_PARTS_SEPARATOR);
|
||||||
let securityContexts: SecurityContext[];
|
let securityContexts: SecurityContext[] = undefined !;
|
||||||
|
|
||||||
// Check check for special cases (prefix style, attr, class)
|
// Check check for special cases (prefix style, attr, class)
|
||||||
if (parts.length > 1) {
|
if (parts.length > 1) {
|
||||||
@ -336,9 +339,9 @@ export class BindingParser {
|
|||||||
name: string, expression: string, sourceSpan: ParseSourceSpan,
|
name: string, expression: string, sourceSpan: ParseSourceSpan,
|
||||||
targetMatchableAttrs: string[][], targetEvents: BoundEventAst[]) {
|
targetMatchableAttrs: string[][], targetEvents: BoundEventAst[]) {
|
||||||
// long format: 'target: eventName'
|
// long format: 'target: eventName'
|
||||||
const [target, eventName] = splitAtColon(name, [null, name]);
|
const [target, eventName] = splitAtColon(name, [null !, name]);
|
||||||
const ast = this._parseAction(expression, sourceSpan);
|
const ast = this._parseAction(expression, sourceSpan);
|
||||||
targetMatchableAttrs.push([name, ast.source]);
|
targetMatchableAttrs.push([name !, ast.source !]);
|
||||||
targetEvents.push(new BoundEventAst(eventName, target, null, ast, sourceSpan));
|
targetEvents.push(new BoundEventAst(eventName, target, null, ast, sourceSpan));
|
||||||
// Don't detect directives for event names for now,
|
// Don't detect directives for event names for now,
|
||||||
// so don't add the event name to the matchableAttrs
|
// so don't add the event name to the matchableAttrs
|
||||||
@ -405,7 +408,7 @@ export class BindingParser {
|
|||||||
const report = isAttr ? this._schemaRegistry.validateAttribute(propName) :
|
const report = isAttr ? this._schemaRegistry.validateAttribute(propName) :
|
||||||
this._schemaRegistry.validateProperty(propName);
|
this._schemaRegistry.validateProperty(propName);
|
||||||
if (report.error) {
|
if (report.error) {
|
||||||
this._reportError(report.msg, sourceSpan, ParseErrorLevel.ERROR);
|
this._reportError(report.msg !, sourceSpan, ParseErrorLevel.ERROR);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -19,7 +19,7 @@ export interface TemplateAst {
|
|||||||
/**
|
/**
|
||||||
* The source span from which this node was parsed.
|
* The source span from which this node was parsed.
|
||||||
*/
|
*/
|
||||||
sourceSpan: ParseSourceSpan;
|
sourceSpan: ParseSourceSpan|null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Visit this node and possibly transform it.
|
* Visit this node and possibly transform it.
|
||||||
@ -62,7 +62,7 @@ export class AttrAst implements TemplateAst {
|
|||||||
export class BoundElementPropertyAst implements TemplateAst {
|
export class BoundElementPropertyAst implements TemplateAst {
|
||||||
constructor(
|
constructor(
|
||||||
public name: string, public type: PropertyBindingType,
|
public name: string, public type: PropertyBindingType,
|
||||||
public securityContext: SecurityContext, public value: AST, public unit: string,
|
public securityContext: SecurityContext, public value: AST, public unit: string|null,
|
||||||
public sourceSpan: ParseSourceSpan) {}
|
public sourceSpan: ParseSourceSpan) {}
|
||||||
visit(visitor: TemplateAstVisitor, context: any): any {
|
visit(visitor: TemplateAstVisitor, context: any): any {
|
||||||
return visitor.visitElementProperty(this, context);
|
return visitor.visitElementProperty(this, context);
|
||||||
@ -75,7 +75,7 @@ export class BoundElementPropertyAst implements TemplateAst {
|
|||||||
* `(@trigger.phase)="callback($event)"`).
|
* `(@trigger.phase)="callback($event)"`).
|
||||||
*/
|
*/
|
||||||
export class BoundEventAst implements TemplateAst {
|
export class BoundEventAst implements TemplateAst {
|
||||||
static calcFullName(name: string, target: string, phase: string): string {
|
static calcFullName(name: string, target: string|null, phase: string|null): string {
|
||||||
if (target) {
|
if (target) {
|
||||||
return `${target}:${name}`;
|
return `${target}:${name}`;
|
||||||
} else if (phase) {
|
} else if (phase) {
|
||||||
@ -86,8 +86,8 @@ export class BoundEventAst implements TemplateAst {
|
|||||||
}
|
}
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
public name: string, public target: string, public phase: string, public handler: AST,
|
public name: string, public target: string|null, public phase: string|null,
|
||||||
public sourceSpan: ParseSourceSpan) {}
|
public handler: AST, public sourceSpan: ParseSourceSpan) {}
|
||||||
visit(visitor: TemplateAstVisitor, context: any): any {
|
visit(visitor: TemplateAstVisitor, context: any): any {
|
||||||
return visitor.visitEvent(this, context);
|
return visitor.visitEvent(this, context);
|
||||||
}
|
}
|
||||||
@ -126,8 +126,8 @@ export class ElementAst implements TemplateAst {
|
|||||||
public outputs: BoundEventAst[], public references: ReferenceAst[],
|
public outputs: BoundEventAst[], public references: ReferenceAst[],
|
||||||
public directives: DirectiveAst[], public providers: ProviderAst[],
|
public directives: DirectiveAst[], public providers: ProviderAst[],
|
||||||
public hasViewContainer: boolean, public queryMatches: QueryMatch[],
|
public hasViewContainer: boolean, public queryMatches: QueryMatch[],
|
||||||
public children: TemplateAst[], public ngContentIndex: number,
|
public children: TemplateAst[], public ngContentIndex: number|null,
|
||||||
public sourceSpan: ParseSourceSpan, public endSourceSpan: ParseSourceSpan) {}
|
public sourceSpan: ParseSourceSpan|null, public endSourceSpan: ParseSourceSpan|null) {}
|
||||||
|
|
||||||
visit(visitor: TemplateAstVisitor, context: any): any {
|
visit(visitor: TemplateAstVisitor, context: any): any {
|
||||||
return visitor.visitElement(this, context);
|
return visitor.visitElement(this, context);
|
||||||
@ -275,7 +275,7 @@ export function templateVisitAll(
|
|||||||
visitor: TemplateAstVisitor, asts: TemplateAst[], context: any = null): any[] {
|
visitor: TemplateAstVisitor, asts: TemplateAst[], context: any = null): any[] {
|
||||||
const result: any[] = [];
|
const result: any[] = [];
|
||||||
const visit = visitor.visit ?
|
const visit = visitor.visit ?
|
||||||
(ast: TemplateAst) => visitor.visit(ast, context) || ast.visit(visitor, context) :
|
(ast: TemplateAst) => visitor.visit !(ast, context) || ast.visit(visitor, context) :
|
||||||
(ast: TemplateAst) => ast.visit(visitor, context);
|
(ast: TemplateAst) => ast.visit(visitor, context);
|
||||||
asts.forEach(ast => {
|
asts.forEach(ast => {
|
||||||
const astResult = visit(ast);
|
const astResult = visit(ast);
|
||||||
|
@ -115,11 +115,11 @@ export class TemplateParser {
|
|||||||
templateUrl: string): {template: TemplateAst[], pipes: CompilePipeSummary[]} {
|
templateUrl: string): {template: TemplateAst[], pipes: CompilePipeSummary[]} {
|
||||||
const result = this.tryParse(component, template, directives, pipes, schemas, templateUrl);
|
const result = this.tryParse(component, template, directives, pipes, schemas, templateUrl);
|
||||||
const warnings =
|
const warnings =
|
||||||
result.errors.filter(error => error.level === ParseErrorLevel.WARNING).filter(warnOnlyOnce([
|
result.errors !.filter(error => error.level === ParseErrorLevel.WARNING)
|
||||||
TEMPLATE_ATTR_DEPRECATION_WARNING, TEMPLATE_ELEMENT_DEPRECATION_WARNING
|
.filter(warnOnlyOnce(
|
||||||
]));
|
[TEMPLATE_ATTR_DEPRECATION_WARNING, TEMPLATE_ELEMENT_DEPRECATION_WARNING]));
|
||||||
|
|
||||||
const errors = result.errors.filter(error => error.level === ParseErrorLevel.ERROR);
|
const errors = result.errors !.filter(error => error.level === ParseErrorLevel.ERROR);
|
||||||
|
|
||||||
if (warnings.length > 0) {
|
if (warnings.length > 0) {
|
||||||
this._console.warn(`Template parse warnings:\n${warnings.join('\n')}`);
|
this._console.warn(`Template parse warnings:\n${warnings.join('\n')}`);
|
||||||
@ -130,7 +130,7 @@ export class TemplateParser {
|
|||||||
throw syntaxError(`Template parse errors:\n${errorString}`);
|
throw syntaxError(`Template parse errors:\n${errorString}`);
|
||||||
}
|
}
|
||||||
|
|
||||||
return {template: result.templateAst, pipes: result.usedPipes};
|
return {template: result.templateAst !, pipes: result.usedPipes !};
|
||||||
}
|
}
|
||||||
|
|
||||||
tryParse(
|
tryParse(
|
||||||
@ -138,7 +138,7 @@ export class TemplateParser {
|
|||||||
pipes: CompilePipeSummary[], schemas: SchemaMetadata[],
|
pipes: CompilePipeSummary[], schemas: SchemaMetadata[],
|
||||||
templateUrl: string): TemplateParseResult {
|
templateUrl: string): TemplateParseResult {
|
||||||
return this.tryParseHtml(
|
return this.tryParseHtml(
|
||||||
this.expandHtml(this._htmlParser.parse(
|
this.expandHtml(this._htmlParser !.parse(
|
||||||
template, templateUrl, true, this.getInterpolationConfig(component))),
|
template, templateUrl, true, this.getInterpolationConfig(component))),
|
||||||
component, template, directives, pipes, schemas, templateUrl);
|
component, template, directives, pipes, schemas, templateUrl);
|
||||||
}
|
}
|
||||||
@ -154,7 +154,7 @@ export class TemplateParser {
|
|||||||
const uniqDirectives = removeSummaryDuplicates(directives);
|
const uniqDirectives = removeSummaryDuplicates(directives);
|
||||||
const uniqPipes = removeSummaryDuplicates(pipes);
|
const uniqPipes = removeSummaryDuplicates(pipes);
|
||||||
const providerViewContext = new ProviderViewContext(component);
|
const providerViewContext = new ProviderViewContext(component);
|
||||||
let interpolationConfig: InterpolationConfig;
|
let interpolationConfig: InterpolationConfig = undefined !;
|
||||||
if (component.template && component.template.interpolation) {
|
if (component.template && component.template.interpolation) {
|
||||||
interpolationConfig = {
|
interpolationConfig = {
|
||||||
start: component.template.interpolation[0],
|
start: component.template.interpolation[0],
|
||||||
@ -162,7 +162,7 @@ export class TemplateParser {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
const bindingParser = new BindingParser(
|
const bindingParser = new BindingParser(
|
||||||
this._exprParser, interpolationConfig, this._schemaRegistry, uniqPipes, errors);
|
this._exprParser, interpolationConfig !, this._schemaRegistry, uniqPipes, errors);
|
||||||
const parseVisitor = new TemplateParseVisitor(
|
const parseVisitor = new TemplateParseVisitor(
|
||||||
this._config, providerViewContext, uniqDirectives, bindingParser, this._schemaRegistry,
|
this._config, providerViewContext, uniqDirectives, bindingParser, this._schemaRegistry,
|
||||||
schemas, errors);
|
schemas, errors);
|
||||||
@ -198,10 +198,11 @@ export class TemplateParser {
|
|||||||
return htmlAstWithErrors;
|
return htmlAstWithErrors;
|
||||||
}
|
}
|
||||||
|
|
||||||
getInterpolationConfig(component: CompileDirectiveMetadata): InterpolationConfig {
|
getInterpolationConfig(component: CompileDirectiveMetadata): InterpolationConfig|undefined {
|
||||||
if (component.template) {
|
if (component.template) {
|
||||||
return InterpolationConfig.fromArray(component.template.interpolation);
|
return InterpolationConfig.fromArray(component.template.interpolation);
|
||||||
}
|
}
|
||||||
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @internal */
|
/** @internal */
|
||||||
@ -238,7 +239,7 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
// Note: queries start with id 1 so we can use the number in a Bloom filter!
|
// Note: queries start with id 1 so we can use the number in a Bloom filter!
|
||||||
this.contentQueryStartId = providerViewContext.component.viewQueries.length + 1;
|
this.contentQueryStartId = providerViewContext.component.viewQueries.length + 1;
|
||||||
directives.forEach((directive, index) => {
|
directives.forEach((directive, index) => {
|
||||||
const selector = CssSelector.parse(directive.selector);
|
const selector = CssSelector.parse(directive.selector !);
|
||||||
this.selectorMatcher.addSelectables(selector, directive);
|
this.selectorMatcher.addSelectables(selector, directive);
|
||||||
this.directivesIndex.set(directive, index);
|
this.directivesIndex.set(directive, index);
|
||||||
});
|
});
|
||||||
@ -249,10 +250,10 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
visitExpansionCase(expansionCase: html.ExpansionCase, context: any): any { return null; }
|
visitExpansionCase(expansionCase: html.ExpansionCase, context: any): any { return null; }
|
||||||
|
|
||||||
visitText(text: html.Text, parent: ElementContext): any {
|
visitText(text: html.Text, parent: ElementContext): any {
|
||||||
const ngContentIndex = parent.findNgContentIndex(TEXT_CSS_SELECTOR);
|
const ngContentIndex = parent.findNgContentIndex(TEXT_CSS_SELECTOR) !;
|
||||||
const expr = this._bindingParser.parseInterpolation(text.value, text.sourceSpan);
|
const expr = this._bindingParser.parseInterpolation(text.value, text.sourceSpan !);
|
||||||
return expr ? new BoundTextAst(expr, ngContentIndex, text.sourceSpan) :
|
return expr ? new BoundTextAst(expr, ngContentIndex, text.sourceSpan !) :
|
||||||
new TextAst(text.value, ngContentIndex, text.sourceSpan);
|
new TextAst(text.value, ngContentIndex, text.sourceSpan !);
|
||||||
}
|
}
|
||||||
|
|
||||||
visitAttribute(attribute: html.Attribute, context: any): any {
|
visitAttribute(attribute: html.Attribute, context: any): any {
|
||||||
@ -322,7 +323,7 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
}
|
}
|
||||||
hasInlineTemplates = true;
|
hasInlineTemplates = true;
|
||||||
this._bindingParser.parseInlineTemplateBinding(
|
this._bindingParser.parseInlineTemplateBinding(
|
||||||
prefixToken, templateBindingsSource, attr.sourceSpan, templateMatchableAttrs,
|
prefixToken !, templateBindingsSource !, attr.sourceSpan, templateMatchableAttrs,
|
||||||
templateElementOrDirectiveProps, templateElementVars);
|
templateElementOrDirectiveProps, templateElementVars);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -340,48 +341,49 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
const boundDirectivePropNames = new Set<string>();
|
const boundDirectivePropNames = new Set<string>();
|
||||||
const directiveAsts = this._createDirectiveAsts(
|
const directiveAsts = this._createDirectiveAsts(
|
||||||
isTemplateElement, element.name, directiveMetas, elementOrDirectiveProps,
|
isTemplateElement, element.name, directiveMetas, elementOrDirectiveProps,
|
||||||
elementOrDirectiveRefs, element.sourceSpan, references, boundDirectivePropNames);
|
elementOrDirectiveRefs, element.sourceSpan !, references, boundDirectivePropNames);
|
||||||
const elementProps: BoundElementPropertyAst[] = this._createElementPropertyAsts(
|
const elementProps: BoundElementPropertyAst[] = this._createElementPropertyAsts(
|
||||||
element.name, elementOrDirectiveProps, boundDirectivePropNames);
|
element.name, elementOrDirectiveProps, boundDirectivePropNames);
|
||||||
const isViewRoot = parent.isTemplateElement || hasInlineTemplates;
|
const isViewRoot = parent.isTemplateElement || hasInlineTemplates;
|
||||||
|
|
||||||
const providerContext = new ProviderElementContext(
|
const providerContext = new ProviderElementContext(
|
||||||
this.providerViewContext, parent.providerContext, isViewRoot, directiveAsts, attrs,
|
this.providerViewContext, parent.providerContext !, isViewRoot, directiveAsts, attrs,
|
||||||
references, isTemplateElement, queryStartIndex, element.sourceSpan);
|
references, isTemplateElement, queryStartIndex, element.sourceSpan !);
|
||||||
|
|
||||||
const children: TemplateAst[] = html.visitAll(
|
const children: TemplateAst[] = html.visitAll(
|
||||||
preparsedElement.nonBindable ? NON_BINDABLE_VISITOR : this, element.children,
|
preparsedElement.nonBindable ? NON_BINDABLE_VISITOR : this, element.children,
|
||||||
ElementContext.create(
|
ElementContext.create(
|
||||||
isTemplateElement, directiveAsts,
|
isTemplateElement, directiveAsts,
|
||||||
isTemplateElement ? parent.providerContext : providerContext));
|
isTemplateElement ? parent.providerContext ! : providerContext));
|
||||||
providerContext.afterElement();
|
providerContext.afterElement();
|
||||||
// Override the actual selector when the `ngProjectAs` attribute is provided
|
// Override the actual selector when the `ngProjectAs` attribute is provided
|
||||||
const projectionSelector = preparsedElement.projectAs != null ?
|
const projectionSelector = preparsedElement.projectAs != null ?
|
||||||
CssSelector.parse(preparsedElement.projectAs)[0] :
|
CssSelector.parse(preparsedElement.projectAs)[0] :
|
||||||
elementCssSelector;
|
elementCssSelector;
|
||||||
const ngContentIndex = parent.findNgContentIndex(projectionSelector);
|
const ngContentIndex = parent.findNgContentIndex(projectionSelector) !;
|
||||||
let parsedElement: TemplateAst;
|
let parsedElement: TemplateAst;
|
||||||
|
|
||||||
if (preparsedElement.type === PreparsedElementType.NG_CONTENT) {
|
if (preparsedElement.type === PreparsedElementType.NG_CONTENT) {
|
||||||
if (element.children && !element.children.every(_isEmptyTextNode)) {
|
if (element.children && !element.children.every(_isEmptyTextNode)) {
|
||||||
this._reportError(`<ng-content> element cannot have content.`, element.sourceSpan);
|
this._reportError(`<ng-content> element cannot have content.`, element.sourceSpan !);
|
||||||
}
|
}
|
||||||
|
|
||||||
parsedElement = new NgContentAst(
|
parsedElement = new NgContentAst(
|
||||||
this.ngContentCount++, hasInlineTemplates ? null : ngContentIndex, element.sourceSpan);
|
this.ngContentCount++, hasInlineTemplates ? null ! : ngContentIndex,
|
||||||
|
element.sourceSpan !);
|
||||||
} else if (isTemplateElement) {
|
} else if (isTemplateElement) {
|
||||||
this._assertAllEventsPublishedByDirectives(directiveAsts, events);
|
this._assertAllEventsPublishedByDirectives(directiveAsts, events);
|
||||||
this._assertNoComponentsNorElementBindingsOnTemplate(
|
this._assertNoComponentsNorElementBindingsOnTemplate(
|
||||||
directiveAsts, elementProps, element.sourceSpan);
|
directiveAsts, elementProps, element.sourceSpan !);
|
||||||
|
|
||||||
parsedElement = new EmbeddedTemplateAst(
|
parsedElement = new EmbeddedTemplateAst(
|
||||||
attrs, events, references, elementVars, providerContext.transformedDirectiveAsts,
|
attrs, events, references, elementVars, providerContext.transformedDirectiveAsts,
|
||||||
providerContext.transformProviders, providerContext.transformedHasViewContainer,
|
providerContext.transformProviders, providerContext.transformedHasViewContainer,
|
||||||
providerContext.queryMatches, children, hasInlineTemplates ? null : ngContentIndex,
|
providerContext.queryMatches, children, hasInlineTemplates ? null ! : ngContentIndex,
|
||||||
element.sourceSpan);
|
element.sourceSpan !);
|
||||||
} else {
|
} else {
|
||||||
this._assertElementExists(matchElement, element);
|
this._assertElementExists(matchElement, element);
|
||||||
this._assertOnlyOneComponent(directiveAsts, element.sourceSpan);
|
this._assertOnlyOneComponent(directiveAsts, element.sourceSpan !);
|
||||||
|
|
||||||
const ngContentIndex =
|
const ngContentIndex =
|
||||||
hasInlineTemplates ? null : parent.findNgContentIndex(projectionSelector);
|
hasInlineTemplates ? null : parent.findNgContentIndex(projectionSelector);
|
||||||
@ -389,7 +391,8 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
nodeName, attrs, elementProps, events, references,
|
nodeName, attrs, elementProps, events, references,
|
||||||
providerContext.transformedDirectiveAsts, providerContext.transformProviders,
|
providerContext.transformedDirectiveAsts, providerContext.transformProviders,
|
||||||
providerContext.transformedHasViewContainer, providerContext.queryMatches, children,
|
providerContext.transformedHasViewContainer, providerContext.queryMatches, children,
|
||||||
hasInlineTemplates ? null : ngContentIndex, element.sourceSpan, element.endSourceSpan);
|
hasInlineTemplates ? null : ngContentIndex, element.sourceSpan || null,
|
||||||
|
element.endSourceSpan || null);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (hasInlineTemplates) {
|
if (hasInlineTemplates) {
|
||||||
@ -400,21 +403,21 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
const templateBoundDirectivePropNames = new Set<string>();
|
const templateBoundDirectivePropNames = new Set<string>();
|
||||||
const templateDirectiveAsts = this._createDirectiveAsts(
|
const templateDirectiveAsts = this._createDirectiveAsts(
|
||||||
true, element.name, templateDirectiveMetas, templateElementOrDirectiveProps, [],
|
true, element.name, templateDirectiveMetas, templateElementOrDirectiveProps, [],
|
||||||
element.sourceSpan, [], templateBoundDirectivePropNames);
|
element.sourceSpan !, [], templateBoundDirectivePropNames);
|
||||||
const templateElementProps: BoundElementPropertyAst[] = this._createElementPropertyAsts(
|
const templateElementProps: BoundElementPropertyAst[] = this._createElementPropertyAsts(
|
||||||
element.name, templateElementOrDirectiveProps, templateBoundDirectivePropNames);
|
element.name, templateElementOrDirectiveProps, templateBoundDirectivePropNames);
|
||||||
this._assertNoComponentsNorElementBindingsOnTemplate(
|
this._assertNoComponentsNorElementBindingsOnTemplate(
|
||||||
templateDirectiveAsts, templateElementProps, element.sourceSpan);
|
templateDirectiveAsts, templateElementProps, element.sourceSpan !);
|
||||||
const templateProviderContext = new ProviderElementContext(
|
const templateProviderContext = new ProviderElementContext(
|
||||||
this.providerViewContext, parent.providerContext, parent.isTemplateElement,
|
this.providerViewContext, parent.providerContext !, parent.isTemplateElement,
|
||||||
templateDirectiveAsts, [], [], true, templateQueryStartIndex, element.sourceSpan);
|
templateDirectiveAsts, [], [], true, templateQueryStartIndex, element.sourceSpan !);
|
||||||
templateProviderContext.afterElement();
|
templateProviderContext.afterElement();
|
||||||
|
|
||||||
parsedElement = new EmbeddedTemplateAst(
|
parsedElement = new EmbeddedTemplateAst(
|
||||||
[], [], [], templateElementVars, templateProviderContext.transformedDirectiveAsts,
|
[], [], [], templateElementVars, templateProviderContext.transformedDirectiveAsts,
|
||||||
templateProviderContext.transformProviders,
|
templateProviderContext.transformProviders,
|
||||||
templateProviderContext.transformedHasViewContainer, templateProviderContext.queryMatches,
|
templateProviderContext.transformedHasViewContainer, templateProviderContext.queryMatches,
|
||||||
[parsedElement], ngContentIndex, element.sourceSpan);
|
[parsedElement], ngContentIndex, element.sourceSpan !);
|
||||||
}
|
}
|
||||||
|
|
||||||
return parsedElement;
|
return parsedElement;
|
||||||
@ -531,7 +534,7 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
let matchElement = false;
|
let matchElement = false;
|
||||||
|
|
||||||
selectorMatcher.match(elementCssSelector, (selector, directive) => {
|
selectorMatcher.match(elementCssSelector, (selector, directive) => {
|
||||||
directives[this.directivesIndex.get(directive)] = directive;
|
directives[this.directivesIndex.get(directive) !] = directive;
|
||||||
matchElement = matchElement || selector.hasElementSelector();
|
matchElement = matchElement || selector.hasElementSelector();
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -547,7 +550,7 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
elementSourceSpan: ParseSourceSpan, targetReferences: ReferenceAst[],
|
elementSourceSpan: ParseSourceSpan, targetReferences: ReferenceAst[],
|
||||||
targetBoundDirectivePropNames: Set<string>): DirectiveAst[] {
|
targetBoundDirectivePropNames: Set<string>): DirectiveAst[] {
|
||||||
const matchedReferences = new Set<string>();
|
const matchedReferences = new Set<string>();
|
||||||
let component: CompileDirectiveSummary = null;
|
let component: CompileDirectiveSummary = null !;
|
||||||
|
|
||||||
const directiveAsts = directives.map((directive) => {
|
const directiveAsts = directives.map((directive) => {
|
||||||
const sourceSpan = new ParseSourceSpan(
|
const sourceSpan = new ParseSourceSpan(
|
||||||
@ -559,11 +562,11 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
}
|
}
|
||||||
const directiveProperties: BoundDirectivePropertyAst[] = [];
|
const directiveProperties: BoundDirectivePropertyAst[] = [];
|
||||||
let hostProperties =
|
let hostProperties =
|
||||||
this._bindingParser.createDirectiveHostPropertyAsts(directive, elementName, sourceSpan);
|
this._bindingParser.createDirectiveHostPropertyAsts(directive, elementName, sourceSpan) !;
|
||||||
// Note: We need to check the host properties here as well,
|
// Note: We need to check the host properties here as well,
|
||||||
// as we don't know the element name in the DirectiveWrapperCompiler yet.
|
// as we don't know the element name in the DirectiveWrapperCompiler yet.
|
||||||
hostProperties = this._checkPropertiesInSchema(elementName, hostProperties);
|
hostProperties = this._checkPropertiesInSchema(elementName, hostProperties);
|
||||||
const hostEvents = this._bindingParser.createDirectiveHostEventAsts(directive, sourceSpan);
|
const hostEvents = this._bindingParser.createDirectiveHostEventAsts(directive, sourceSpan) !;
|
||||||
this._createDirectivePropertyAsts(
|
this._createDirectivePropertyAsts(
|
||||||
directive.inputs, props, directiveProperties, targetBoundDirectivePropNames);
|
directive.inputs, props, directiveProperties, targetBoundDirectivePropNames);
|
||||||
elementOrDirectiveRefs.forEach((elOrDirRef) => {
|
elementOrDirectiveRefs.forEach((elOrDirRef) => {
|
||||||
@ -589,7 +592,7 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
elOrDirRef.sourceSpan);
|
elOrDirRef.sourceSpan);
|
||||||
}
|
}
|
||||||
} else if (!component) {
|
} else if (!component) {
|
||||||
let refToken: CompileTokenMetadata = null;
|
let refToken: CompileTokenMetadata = null !;
|
||||||
if (isTemplateElement) {
|
if (isTemplateElement) {
|
||||||
refToken = createIdentifierToken(Identifiers.TemplateRef);
|
refToken = createIdentifierToken(Identifiers.TemplateRef);
|
||||||
}
|
}
|
||||||
@ -648,7 +651,7 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
|
|
||||||
private _findComponentDirectiveNames(directives: DirectiveAst[]): string[] {
|
private _findComponentDirectiveNames(directives: DirectiveAst[]): string[] {
|
||||||
return this._findComponentDirectives(directives)
|
return this._findComponentDirectives(directives)
|
||||||
.map(directive => identifierName(directive.directive.type));
|
.map(directive => identifierName(directive.directive.type) !);
|
||||||
}
|
}
|
||||||
|
|
||||||
private _assertOnlyOneComponent(directives: DirectiveAst[], sourceSpan: ParseSourceSpan) {
|
private _assertOnlyOneComponent(directives: DirectiveAst[], sourceSpan: ParseSourceSpan) {
|
||||||
@ -685,7 +688,7 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
errorMsg +=
|
errorMsg +=
|
||||||
`2. To allow any element add 'NO_ERRORS_SCHEMA' to the '@NgModule.schemas' of this component.`;
|
`2. To allow any element add 'NO_ERRORS_SCHEMA' to the '@NgModule.schemas' of this component.`;
|
||||||
}
|
}
|
||||||
this._reportError(errorMsg, element.sourceSpan);
|
this._reportError(errorMsg, element.sourceSpan !);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -757,7 +760,7 @@ class TemplateParseVisitor implements html.Visitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class NonBindableVisitor implements html.Visitor {
|
class NonBindableVisitor implements html.Visitor {
|
||||||
visitElement(ast: html.Element, parent: ElementContext): ElementAst {
|
visitElement(ast: html.Element, parent: ElementContext): ElementAst|null {
|
||||||
const preparsedElement = preparseElement(ast);
|
const preparsedElement = preparseElement(ast);
|
||||||
if (preparsedElement.type === PreparsedElementType.SCRIPT ||
|
if (preparsedElement.type === PreparsedElementType.SCRIPT ||
|
||||||
preparsedElement.type === PreparsedElementType.STYLE ||
|
preparsedElement.type === PreparsedElementType.STYLE ||
|
||||||
@ -783,8 +786,8 @@ class NonBindableVisitor implements html.Visitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
visitText(text: html.Text, parent: ElementContext): TextAst {
|
visitText(text: html.Text, parent: ElementContext): TextAst {
|
||||||
const ngContentIndex = parent.findNgContentIndex(TEXT_CSS_SELECTOR);
|
const ngContentIndex = parent.findNgContentIndex(TEXT_CSS_SELECTOR) !;
|
||||||
return new TextAst(text.value, ngContentIndex, text.sourceSpan);
|
return new TextAst(text.value, ngContentIndex, text.sourceSpan !);
|
||||||
}
|
}
|
||||||
|
|
||||||
visitExpansion(expansion: html.Expansion, context: any): any { return expansion; }
|
visitExpansion(expansion: html.Expansion, context: any): any { return expansion; }
|
||||||
@ -805,10 +808,10 @@ class ElementContext {
|
|||||||
isTemplateElement: boolean, directives: DirectiveAst[],
|
isTemplateElement: boolean, directives: DirectiveAst[],
|
||||||
providerContext: ProviderElementContext): ElementContext {
|
providerContext: ProviderElementContext): ElementContext {
|
||||||
const matcher = new SelectorMatcher();
|
const matcher = new SelectorMatcher();
|
||||||
let wildcardNgContentIndex: number = null;
|
let wildcardNgContentIndex: number = null !;
|
||||||
const component = directives.find(directive => directive.directive.isComponent);
|
const component = directives.find(directive => directive.directive.isComponent);
|
||||||
if (component) {
|
if (component) {
|
||||||
const ngContentSelectors = component.directive.template.ngContentSelectors;
|
const ngContentSelectors = component.directive.template !.ngContentSelectors;
|
||||||
for (let i = 0; i < ngContentSelectors.length; i++) {
|
for (let i = 0; i < ngContentSelectors.length; i++) {
|
||||||
const selector = ngContentSelectors[i];
|
const selector = ngContentSelectors[i];
|
||||||
if (selector === '*') {
|
if (selector === '*') {
|
||||||
@ -822,9 +825,10 @@ class ElementContext {
|
|||||||
}
|
}
|
||||||
constructor(
|
constructor(
|
||||||
public isTemplateElement: boolean, private _ngContentIndexMatcher: SelectorMatcher,
|
public isTemplateElement: boolean, private _ngContentIndexMatcher: SelectorMatcher,
|
||||||
private _wildcardNgContentIndex: number, public providerContext: ProviderElementContext) {}
|
private _wildcardNgContentIndex: number|null,
|
||||||
|
public providerContext: ProviderElementContext|null) {}
|
||||||
|
|
||||||
findNgContentIndex(selector: CssSelector): number {
|
findNgContentIndex(selector: CssSelector): number|null {
|
||||||
const ngContentIndices: number[] = [];
|
const ngContentIndices: number[] = [];
|
||||||
this._ngContentIndexMatcher.match(
|
this._ngContentIndexMatcher.match(
|
||||||
selector, (selector, ngContentIndex) => { ngContentIndices.push(ngContentIndex); });
|
selector, (selector, ngContentIndex) => { ngContentIndices.push(ngContentIndex); });
|
||||||
@ -893,10 +897,9 @@ function isTemplate(
|
|||||||
// `<template>` is HTML and case insensitive
|
// `<template>` is HTML and case insensitive
|
||||||
if (tagNoNs.toLowerCase() === TEMPLATE_ELEMENT) {
|
if (tagNoNs.toLowerCase() === TEMPLATE_ELEMENT) {
|
||||||
if (enableLegacyTemplate && tagNoNs.toLowerCase() === TEMPLATE_ELEMENT) {
|
if (enableLegacyTemplate && tagNoNs.toLowerCase() === TEMPLATE_ELEMENT) {
|
||||||
reportDeprecation(TEMPLATE_ELEMENT_DEPRECATION_WARNING, el.sourceSpan);
|
reportDeprecation(TEMPLATE_ELEMENT_DEPRECATION_WARNING, el.sourceSpan !);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -21,11 +21,11 @@ const NG_NON_BINDABLE_ATTR = 'ngNonBindable';
|
|||||||
const NG_PROJECT_AS = 'ngProjectAs';
|
const NG_PROJECT_AS = 'ngProjectAs';
|
||||||
|
|
||||||
export function preparseElement(ast: html.Element): PreparsedElement {
|
export function preparseElement(ast: html.Element): PreparsedElement {
|
||||||
let selectAttr: string = null;
|
let selectAttr: string = null !;
|
||||||
let hrefAttr: string = null;
|
let hrefAttr: string = null !;
|
||||||
let relAttr: string = null;
|
let relAttr: string = null !;
|
||||||
let nonBindable = false;
|
let nonBindable = false;
|
||||||
let projectAs: string = null;
|
let projectAs: string = null !;
|
||||||
ast.attrs.forEach(attr => {
|
ast.attrs.forEach(attr => {
|
||||||
const lcAttrName = attr.name.toLowerCase();
|
const lcAttrName = attr.name.toLowerCase();
|
||||||
if (lcAttrName == NG_CONTENT_SELECT_ATTR) {
|
if (lcAttrName == NG_CONTENT_SELECT_ATTR) {
|
||||||
|
@ -49,7 +49,7 @@ export const DEFAULT_PACKAGE_URL_PROVIDER = {
|
|||||||
*/
|
*/
|
||||||
@CompilerInjectable()
|
@CompilerInjectable()
|
||||||
export class UrlResolver {
|
export class UrlResolver {
|
||||||
constructor(@Inject(PACKAGE_ROOT_URL) private _packagePrefix: string = null) {}
|
constructor(@Inject(PACKAGE_ROOT_URL) private _packagePrefix: string|null = null) {}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Resolves the `url` given the `baseUrl`:
|
* Resolves the `url` given the `baseUrl`:
|
||||||
@ -254,7 +254,7 @@ enum _ComponentIndex {
|
|||||||
* arbitrary strings may still look like path names.
|
* arbitrary strings may still look like path names.
|
||||||
*/
|
*/
|
||||||
function _split(uri: string): Array<string|any> {
|
function _split(uri: string): Array<string|any> {
|
||||||
return uri.match(_splitRe);
|
return uri.match(_splitRe) !;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -50,6 +50,14 @@ export function visitValue(value: any, visitor: ValueVisitor, context: any): any
|
|||||||
return visitor.visitOther(value, context);
|
return visitor.visitOther(value, context);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function isDefined(val: any): boolean {
|
||||||
|
return val !== null && val !== undefined;
|
||||||
|
}
|
||||||
|
|
||||||
|
export function noUndefined<T>(val: T | undefined): T {
|
||||||
|
return val === undefined ? null ! : val;
|
||||||
|
}
|
||||||
|
|
||||||
export interface ValueVisitor {
|
export interface ValueVisitor {
|
||||||
visitArray(arr: any[], context: any): any;
|
visitArray(arr: any[], context: any): any;
|
||||||
visitStringMap(map: {[key: string]: any}, context: any): any;
|
visitStringMap(map: {[key: string]: any}, context: any): any;
|
||||||
@ -71,7 +79,7 @@ export class ValueTransformer implements ValueVisitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class SyncAsyncResult<T> {
|
export class SyncAsyncResult<T> {
|
||||||
constructor(public syncResult: T, public asyncResult: Promise<T> = null) {
|
constructor(public syncResult: T|null, public asyncResult: Promise<T>|null = null) {
|
||||||
if (!asyncResult) {
|
if (!asyncResult) {
|
||||||
this.asyncResult = Promise.resolve(syncResult);
|
this.asyncResult = Promise.resolve(syncResult);
|
||||||
}
|
}
|
||||||
|
@ -44,22 +44,22 @@ export class ViewCompiler {
|
|||||||
|
|
||||||
const statements: o.Statement[] = [];
|
const statements: o.Statement[] = [];
|
||||||
|
|
||||||
let renderComponentVarName: string;
|
let renderComponentVarName: string = undefined !;
|
||||||
if (!component.isHost) {
|
if (!component.isHost) {
|
||||||
|
const template = component.template !;
|
||||||
const customRenderData: o.LiteralMapEntry[] = [];
|
const customRenderData: o.LiteralMapEntry[] = [];
|
||||||
if (component.template.animations && component.template.animations.length) {
|
if (template.animations && template.animations.length) {
|
||||||
customRenderData.push(new o.LiteralMapEntry(
|
customRenderData.push(
|
||||||
'animation', convertValueToOutputAst(component.template.animations), true));
|
new o.LiteralMapEntry('animation', convertValueToOutputAst(template.animations), true));
|
||||||
}
|
}
|
||||||
|
|
||||||
const renderComponentVar = o.variable(rendererTypeName(component.type.reference));
|
const renderComponentVar = o.variable(rendererTypeName(component.type.reference));
|
||||||
renderComponentVarName = renderComponentVar.name;
|
renderComponentVarName = renderComponentVar.name !;
|
||||||
statements.push(
|
statements.push(
|
||||||
renderComponentVar
|
renderComponentVar
|
||||||
.set(o.importExpr(createIdentifier(Identifiers.createRendererType2))
|
.set(o.importExpr(createIdentifier(Identifiers.createRendererType2))
|
||||||
.callFn([new o.LiteralMapExpr([
|
.callFn([new o.LiteralMapExpr([
|
||||||
new o.LiteralMapEntry(
|
new o.LiteralMapEntry('encapsulation', o.literal(template.encapsulation)),
|
||||||
'encapsulation', o.literal(component.template.encapsulation)),
|
|
||||||
new o.LiteralMapEntry('styles', styles),
|
new o.LiteralMapEntry('styles', styles),
|
||||||
new o.LiteralMapEntry('data', new o.LiteralMapExpr(customRenderData))
|
new o.LiteralMapEntry('data', new o.LiteralMapExpr(customRenderData))
|
||||||
])]))
|
])]))
|
||||||
@ -68,7 +68,7 @@ export class ViewCompiler {
|
|||||||
[o.StmtModifier.Final]));
|
[o.StmtModifier.Final]));
|
||||||
}
|
}
|
||||||
|
|
||||||
const viewBuilderFactory = (parent: ViewBuilder): ViewBuilder => {
|
const viewBuilderFactory = (parent: ViewBuilder | null): ViewBuilder => {
|
||||||
const embeddedViewIndex = embeddedViewCount++;
|
const embeddedViewIndex = embeddedViewCount++;
|
||||||
return new ViewBuilder(
|
return new ViewBuilder(
|
||||||
parent, component, embeddedViewIndex, usedPipes, staticQueryIds, viewBuilderFactory);
|
parent, component, embeddedViewIndex, usedPipes, staticQueryIds, viewBuilderFactory);
|
||||||
@ -105,7 +105,7 @@ const ALLOW_DEFAULT_VAR = o.variable(`ad`);
|
|||||||
class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
||||||
private compType: o.Type;
|
private compType: o.Type;
|
||||||
private nodes: (() => {
|
private nodes: (() => {
|
||||||
sourceSpan: ParseSourceSpan,
|
sourceSpan: ParseSourceSpan | null,
|
||||||
nodeDef: o.Expression,
|
nodeDef: o.Expression,
|
||||||
nodeFlags: NodeFlags, updateDirectives?: UpdateExpression[], updateRenderer?: UpdateExpression[]
|
nodeFlags: NodeFlags, updateDirectives?: UpdateExpression[], updateRenderer?: UpdateExpression[]
|
||||||
})[] = [];
|
})[] = [];
|
||||||
@ -116,14 +116,15 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
private children: ViewBuilder[] = [];
|
private children: ViewBuilder[] = [];
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
private parent: ViewBuilder, private component: CompileDirectiveMetadata,
|
private parent: ViewBuilder|null, private component: CompileDirectiveMetadata,
|
||||||
private embeddedViewIndex: number, private usedPipes: CompilePipeSummary[],
|
private embeddedViewIndex: number, private usedPipes: CompilePipeSummary[],
|
||||||
private staticQueryIds: Map<TemplateAst, StaticAndDynamicQueryIds>,
|
private staticQueryIds: Map<TemplateAst, StaticAndDynamicQueryIds>,
|
||||||
private viewBuilderFactory: ViewBuilderFactory) {
|
private viewBuilderFactory: ViewBuilderFactory) {
|
||||||
// TODO(tbosch): The old view compiler used to use an `any` type
|
// TODO(tbosch): The old view compiler used to use an `any` type
|
||||||
// for the context in any embedded view. We keep this behaivor for now
|
// for the context in any embedded view. We keep this behaivor for now
|
||||||
// to be able to introduce the new view compiler without too many errors.
|
// to be able to introduce the new view compiler without too many errors.
|
||||||
this.compType = this.embeddedViewIndex > 0 ? o.DYNAMIC_TYPE : o.importType(this.component.type);
|
this.compType =
|
||||||
|
this.embeddedViewIndex > 0 ? o.DYNAMIC_TYPE : o.importType(this.component.type) !;
|
||||||
}
|
}
|
||||||
|
|
||||||
get viewName(): string {
|
get viewName(): string {
|
||||||
@ -188,7 +189,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
viewFlags |= ViewFlags.OnPush;
|
viewFlags |= ViewFlags.OnPush;
|
||||||
}
|
}
|
||||||
const viewFactory = new o.DeclareFunctionStmt(
|
const viewFactory = new o.DeclareFunctionStmt(
|
||||||
this.viewName, [new o.FnParam(LOG_VAR.name)],
|
this.viewName, [new o.FnParam(LOG_VAR.name !)],
|
||||||
[new o.ReturnStatement(o.importExpr(createIdentifier(Identifiers.viewDef)).callFn([
|
[new o.ReturnStatement(o.importExpr(createIdentifier(Identifiers.viewDef)).callFn([
|
||||||
o.literal(viewFlags),
|
o.literal(viewFlags),
|
||||||
o.literalArr(nodeDefExprs),
|
o.literalArr(nodeDefExprs),
|
||||||
@ -205,13 +206,13 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
let updateFn: o.Expression;
|
let updateFn: o.Expression;
|
||||||
if (updateStmts.length > 0) {
|
if (updateStmts.length > 0) {
|
||||||
const preStmts: o.Statement[] = [];
|
const preStmts: o.Statement[] = [];
|
||||||
if (!this.component.isHost && o.findReadVarNames(updateStmts).has(COMP_VAR.name)) {
|
if (!this.component.isHost && o.findReadVarNames(updateStmts).has(COMP_VAR.name !)) {
|
||||||
preStmts.push(COMP_VAR.set(VIEW_VAR.prop('component')).toDeclStmt(this.compType));
|
preStmts.push(COMP_VAR.set(VIEW_VAR.prop('component')).toDeclStmt(this.compType));
|
||||||
}
|
}
|
||||||
updateFn = o.fn(
|
updateFn = o.fn(
|
||||||
[
|
[
|
||||||
new o.FnParam(CHECK_VAR.name, o.INFERRED_TYPE),
|
new o.FnParam(CHECK_VAR.name !, o.INFERRED_TYPE),
|
||||||
new o.FnParam(VIEW_VAR.name, o.INFERRED_TYPE)
|
new o.FnParam(VIEW_VAR.name !, o.INFERRED_TYPE)
|
||||||
],
|
],
|
||||||
[...preStmts, ...updateStmts], o.INFERRED_TYPE);
|
[...preStmts, ...updateStmts], o.INFERRED_TYPE);
|
||||||
} else {
|
} else {
|
||||||
@ -245,7 +246,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
visitBoundText(ast: BoundTextAst, context: any): any {
|
visitBoundText(ast: BoundTextAst, context: any): any {
|
||||||
const nodeIndex = this.nodes.length;
|
const nodeIndex = this.nodes.length;
|
||||||
// reserve the space in the nodeDefs array
|
// reserve the space in the nodeDefs array
|
||||||
this.nodes.push(null);
|
this.nodes.push(null !);
|
||||||
|
|
||||||
const astWithSource = <ASTWithSource>ast.value;
|
const astWithSource = <ASTWithSource>ast.value;
|
||||||
const inter = <Interpolation>astWithSource.ast;
|
const inter = <Interpolation>astWithSource.ast;
|
||||||
@ -268,7 +269,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
visitEmbeddedTemplate(ast: EmbeddedTemplateAst, context: any): any {
|
visitEmbeddedTemplate(ast: EmbeddedTemplateAst, context: any): any {
|
||||||
const nodeIndex = this.nodes.length;
|
const nodeIndex = this.nodes.length;
|
||||||
// reserve the space in the nodeDefs array
|
// reserve the space in the nodeDefs array
|
||||||
this.nodes.push(null);
|
this.nodes.push(null !);
|
||||||
|
|
||||||
const {flags, queryMatchesExpr, hostEvents} = this._visitElementOrTemplate(nodeIndex, ast);
|
const {flags, queryMatchesExpr, hostEvents} = this._visitElementOrTemplate(nodeIndex, ast);
|
||||||
|
|
||||||
@ -299,9 +300,9 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
visitElement(ast: ElementAst, context: any): any {
|
visitElement(ast: ElementAst, context: any): any {
|
||||||
const nodeIndex = this.nodes.length;
|
const nodeIndex = this.nodes.length;
|
||||||
// reserve the space in the nodeDefs array so we can add children
|
// reserve the space in the nodeDefs array so we can add children
|
||||||
this.nodes.push(null);
|
this.nodes.push(null !);
|
||||||
|
|
||||||
let elName = ast.name;
|
let elName: string|null = ast.name;
|
||||||
if (ast.name === NG_CONTAINER_TAG) {
|
if (ast.name === NG_CONTAINER_TAG) {
|
||||||
// Using a null element name creates an anchor.
|
// Using a null element name creates an anchor.
|
||||||
elName = null;
|
elName = null;
|
||||||
@ -314,13 +315,13 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
let updateRendererExpressions: UpdateExpression[] = [];
|
let updateRendererExpressions: UpdateExpression[] = [];
|
||||||
let outputDefs: o.Expression[] = [];
|
let outputDefs: o.Expression[] = [];
|
||||||
if (elName) {
|
if (elName) {
|
||||||
const hostBindings = ast.inputs
|
const hostBindings: any[] = ast.inputs
|
||||||
.map((inputAst) => ({
|
.map((inputAst) => ({
|
||||||
context: COMP_VAR as o.Expression,
|
context: COMP_VAR as o.Expression,
|
||||||
inputAst,
|
inputAst,
|
||||||
dirAst: null,
|
dirAst: null as any,
|
||||||
}))
|
}))
|
||||||
.concat(dirHostBindings);
|
.concat(dirHostBindings);
|
||||||
if (hostBindings.length) {
|
if (hostBindings.length) {
|
||||||
updateRendererExpressions =
|
updateRendererExpressions =
|
||||||
hostBindings.map((hostBinding, bindingIndex) => this._preprocessUpdateExpression({
|
hostBindings.map((hostBinding, bindingIndex) => this._preprocessUpdateExpression({
|
||||||
@ -386,7 +387,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
queryMatches: QueryMatch[]
|
queryMatches: QueryMatch[]
|
||||||
}): {
|
}): {
|
||||||
flags: NodeFlags,
|
flags: NodeFlags,
|
||||||
usedEvents: [string, string][],
|
usedEvents: [string | null, string][],
|
||||||
queryMatchesExpr: o.Expression,
|
queryMatchesExpr: o.Expression,
|
||||||
hostBindings:
|
hostBindings:
|
||||||
{context: o.Expression, inputAst: BoundElementPropertyAst, dirAst: DirectiveAst}[],
|
{context: o.Expression, inputAst: BoundElementPropertyAst, dirAst: DirectiveAst}[],
|
||||||
@ -396,7 +397,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
if (ast.hasViewContainer) {
|
if (ast.hasViewContainer) {
|
||||||
flags |= NodeFlags.EmbeddedViews;
|
flags |= NodeFlags.EmbeddedViews;
|
||||||
}
|
}
|
||||||
const usedEvents = new Map<string, [string, string]>();
|
const usedEvents = new Map<string, [string | null, string]>();
|
||||||
ast.outputs.forEach((event) => {
|
ast.outputs.forEach((event) => {
|
||||||
const {name, target} = elementEventNameAndTarget(event, null);
|
const {name, target} = elementEventNameAndTarget(event, null);
|
||||||
usedEvents.set(elementEventFullName(target, name), [target, name]);
|
usedEvents.set(elementEventFullName(target, name), [target, name]);
|
||||||
@ -416,8 +417,8 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
}
|
}
|
||||||
|
|
||||||
ast.providers.forEach((providerAst, providerIndex) => {
|
ast.providers.forEach((providerAst, providerIndex) => {
|
||||||
let dirAst: DirectiveAst;
|
let dirAst: DirectiveAst = undefined !;
|
||||||
let dirIndex: number;
|
let dirIndex: number = undefined !;
|
||||||
ast.directives.forEach((localDirAst, i) => {
|
ast.directives.forEach((localDirAst, i) => {
|
||||||
if (localDirAst.directive.type.reference === tokenReference(providerAst.token)) {
|
if (localDirAst.directive.type.reference === tokenReference(providerAst.token)) {
|
||||||
dirAst = localDirAst;
|
dirAst = localDirAst;
|
||||||
@ -427,7 +428,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
if (dirAst) {
|
if (dirAst) {
|
||||||
const {hostBindings: dirHostBindings, hostEvents: dirHostEvents} = this._visitDirective(
|
const {hostBindings: dirHostBindings, hostEvents: dirHostEvents} = this._visitDirective(
|
||||||
providerAst, dirAst, dirIndex, nodeIndex, ast.references, ast.queryMatches, usedEvents,
|
providerAst, dirAst, dirIndex, nodeIndex, ast.references, ast.queryMatches, usedEvents,
|
||||||
this.staticQueryIds.get(<any>ast));
|
this.staticQueryIds.get(<any>ast) !);
|
||||||
hostBindings.push(...dirHostBindings);
|
hostBindings.push(...dirHostBindings);
|
||||||
hostEvents.push(...dirHostEvents);
|
hostEvents.push(...dirHostEvents);
|
||||||
} else {
|
} else {
|
||||||
@ -437,7 +438,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
|
|
||||||
let queryMatchExprs: o.Expression[] = [];
|
let queryMatchExprs: o.Expression[] = [];
|
||||||
ast.queryMatches.forEach((match) => {
|
ast.queryMatches.forEach((match) => {
|
||||||
let valueType: QueryValueType;
|
let valueType: QueryValueType = undefined !;
|
||||||
if (tokenReference(match.value) === resolveIdentifier(Identifiers.ElementRef)) {
|
if (tokenReference(match.value) === resolveIdentifier(Identifiers.ElementRef)) {
|
||||||
valueType = QueryValueType.ElementRef;
|
valueType = QueryValueType.ElementRef;
|
||||||
} else if (tokenReference(match.value) === resolveIdentifier(Identifiers.ViewContainerRef)) {
|
} else if (tokenReference(match.value) === resolveIdentifier(Identifiers.ViewContainerRef)) {
|
||||||
@ -450,7 +451,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
ast.references.forEach((ref) => {
|
ast.references.forEach((ref) => {
|
||||||
let valueType: QueryValueType;
|
let valueType: QueryValueType = undefined !;
|
||||||
if (!ref.value) {
|
if (!ref.value) {
|
||||||
valueType = QueryValueType.RenderElement;
|
valueType = QueryValueType.RenderElement;
|
||||||
} else if (tokenReference(ref.value) === resolveIdentifier(Identifiers.TemplateRef)) {
|
} else if (tokenReference(ref.value) === resolveIdentifier(Identifiers.TemplateRef)) {
|
||||||
@ -462,7 +463,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
ast.outputs.forEach((outputAst) => {
|
ast.outputs.forEach((outputAst) => {
|
||||||
hostEvents.push({context: COMP_VAR, eventAst: outputAst, dirAst: null});
|
hostEvents.push({context: COMP_VAR, eventAst: outputAst, dirAst: null !});
|
||||||
});
|
});
|
||||||
|
|
||||||
return {
|
return {
|
||||||
@ -470,7 +471,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
usedEvents: Array.from(usedEvents.values()),
|
usedEvents: Array.from(usedEvents.values()),
|
||||||
queryMatchesExpr: queryMatchExprs.length ? o.literalArr(queryMatchExprs) : o.NULL_EXPR,
|
queryMatchesExpr: queryMatchExprs.length ? o.literalArr(queryMatchExprs) : o.NULL_EXPR,
|
||||||
hostBindings,
|
hostBindings,
|
||||||
hostEvents
|
hostEvents: hostEvents
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -484,7 +485,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
} {
|
} {
|
||||||
const nodeIndex = this.nodes.length;
|
const nodeIndex = this.nodes.length;
|
||||||
// reserve the space in the nodeDefs array so we can add children
|
// reserve the space in the nodeDefs array so we can add children
|
||||||
this.nodes.push(null);
|
this.nodes.push(null !);
|
||||||
|
|
||||||
dirAst.directive.queries.forEach((query, queryIndex) => {
|
dirAst.directive.queries.forEach((query, queryIndex) => {
|
||||||
const queryId = dirAst.contentQueryStartId + queryIndex;
|
const queryId = dirAst.contentQueryStartId + queryIndex;
|
||||||
@ -588,7 +589,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
private _visitProvider(providerAst: ProviderAst, queryMatches: QueryMatch[]): void {
|
private _visitProvider(providerAst: ProviderAst, queryMatches: QueryMatch[]): void {
|
||||||
const nodeIndex = this.nodes.length;
|
const nodeIndex = this.nodes.length;
|
||||||
// reserve the space in the nodeDefs array so we can add children
|
// reserve the space in the nodeDefs array so we can add children
|
||||||
this.nodes.push(null);
|
this.nodes.push(null !);
|
||||||
|
|
||||||
const {flags, queryMatchExprs, providerExpr, depsExpr} =
|
const {flags, queryMatchExprs, providerExpr, depsExpr} =
|
||||||
this._visitProviderOrDirective(providerAst, queryMatches);
|
this._visitProviderOrDirective(providerAst, queryMatches);
|
||||||
@ -639,12 +640,12 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
return {flags: flags | providerType, queryMatchExprs, providerExpr, depsExpr};
|
return {flags: flags | providerType, queryMatchExprs, providerExpr, depsExpr};
|
||||||
}
|
}
|
||||||
|
|
||||||
getLocal(name: string): o.Expression {
|
getLocal(name: string): o.Expression|null {
|
||||||
if (name == EventHandlerVars.event.name) {
|
if (name == EventHandlerVars.event.name) {
|
||||||
return EventHandlerVars.event;
|
return EventHandlerVars.event;
|
||||||
}
|
}
|
||||||
let currViewExpr: o.Expression = VIEW_VAR;
|
let currViewExpr: o.Expression = VIEW_VAR;
|
||||||
for (let currBuilder: ViewBuilder = this; currBuilder; currBuilder = currBuilder.parent,
|
for (let currBuilder: ViewBuilder|null = this; currBuilder; currBuilder = currBuilder.parent,
|
||||||
currViewExpr = currViewExpr.prop('parent').cast(o.DYNAMIC_TYPE)) {
|
currViewExpr = currViewExpr.prop('parent').cast(o.DYNAMIC_TYPE)) {
|
||||||
// check references
|
// check references
|
||||||
const refNodeIndex = currBuilder.refNodeIndices[name];
|
const refNodeIndex = currBuilder.refNodeIndices[name];
|
||||||
@ -701,7 +702,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
}
|
}
|
||||||
createPipeConverter(expression: UpdateExpression, name: string, argCount: number):
|
createPipeConverter(expression: UpdateExpression, name: string, argCount: number):
|
||||||
BuiltinConverter {
|
BuiltinConverter {
|
||||||
const pipe = this.usedPipes.find((pipeSummary) => pipeSummary.name === name);
|
const pipe = this.usedPipes.find((pipeSummary) => pipeSummary.name === name) !;
|
||||||
if (pipe.pure) {
|
if (pipe.pure) {
|
||||||
const nodeIndex = this.nodes.length;
|
const nodeIndex = this.nodes.length;
|
||||||
// function purePipeDef(argCount: number): NodeDef;
|
// function purePipeDef(argCount: number): NodeDef;
|
||||||
@ -740,7 +741,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private _createPipe(sourceSpan: ParseSourceSpan, pipe: CompilePipeSummary): number {
|
private _createPipe(sourceSpan: ParseSourceSpan|null, pipe: CompilePipeSummary): number {
|
||||||
const nodeIndex = this.nodes.length;
|
const nodeIndex = this.nodes.length;
|
||||||
let flags = NodeFlags.None;
|
let flags = NodeFlags.None;
|
||||||
pipe.type.lifecycleHooks.forEach((lifecycleHook) => {
|
pipe.type.lifecycleHooks.forEach((lifecycleHook) => {
|
||||||
@ -816,7 +817,7 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
return {updateRendererStmts, updateDirectivesStmts, nodeDefExprs};
|
return {updateRendererStmts, updateDirectivesStmts, nodeDefExprs};
|
||||||
|
|
||||||
function createUpdateStatements(
|
function createUpdateStatements(
|
||||||
nodeIndex: number, sourceSpan: ParseSourceSpan, expressions: UpdateExpression[],
|
nodeIndex: number, sourceSpan: ParseSourceSpan | null, expressions: UpdateExpression[],
|
||||||
allowEmptyExprs: boolean): o.Statement[] {
|
allowEmptyExprs: boolean): o.Statement[] {
|
||||||
const updateStmts: o.Statement[] = [];
|
const updateStmts: o.Statement[] = [];
|
||||||
const exprs = expressions.map(({sourceSpan, context, value}) => {
|
const exprs = expressions.map(({sourceSpan, context, value}) => {
|
||||||
@ -824,8 +825,8 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
const nameResolver = context === COMP_VAR ? self : null;
|
const nameResolver = context === COMP_VAR ? self : null;
|
||||||
const {stmts, currValExpr} =
|
const {stmts, currValExpr} =
|
||||||
convertPropertyBinding(nameResolver, context, value, bindingId);
|
convertPropertyBinding(nameResolver, context, value, bindingId);
|
||||||
updateStmts.push(
|
updateStmts.push(...stmts.map(
|
||||||
...stmts.map(stmt => o.applySourceSpanToStatementIfNeeded(stmt, sourceSpan)));
|
(stmt: o.Statement) => o.applySourceSpanToStatementIfNeeded(stmt, sourceSpan)));
|
||||||
return o.applySourceSpanToExpressionIfNeeded(currValExpr, sourceSpan);
|
return o.applySourceSpanToExpressionIfNeeded(currValExpr, sourceSpan);
|
||||||
});
|
});
|
||||||
if (expressions.length || allowEmptyExprs) {
|
if (expressions.length || allowEmptyExprs) {
|
||||||
@ -860,14 +861,14 @@ class ViewBuilder implements TemplateAstVisitor, LocalResolver {
|
|||||||
if (handleEventStmts.length > 0) {
|
if (handleEventStmts.length > 0) {
|
||||||
const preStmts: o.Statement[] =
|
const preStmts: o.Statement[] =
|
||||||
[ALLOW_DEFAULT_VAR.set(o.literal(true)).toDeclStmt(o.BOOL_TYPE)];
|
[ALLOW_DEFAULT_VAR.set(o.literal(true)).toDeclStmt(o.BOOL_TYPE)];
|
||||||
if (!this.component.isHost && o.findReadVarNames(handleEventStmts).has(COMP_VAR.name)) {
|
if (!this.component.isHost && o.findReadVarNames(handleEventStmts).has(COMP_VAR.name !)) {
|
||||||
preStmts.push(COMP_VAR.set(VIEW_VAR.prop('component')).toDeclStmt(this.compType));
|
preStmts.push(COMP_VAR.set(VIEW_VAR.prop('component')).toDeclStmt(this.compType));
|
||||||
}
|
}
|
||||||
handleEventFn = o.fn(
|
handleEventFn = o.fn(
|
||||||
[
|
[
|
||||||
new o.FnParam(VIEW_VAR.name, o.INFERRED_TYPE),
|
new o.FnParam(VIEW_VAR.name !, o.INFERRED_TYPE),
|
||||||
new o.FnParam(EVENT_NAME_VAR.name, o.INFERRED_TYPE),
|
new o.FnParam(EVENT_NAME_VAR.name !, o.INFERRED_TYPE),
|
||||||
new o.FnParam(EventHandlerVars.event.name, o.INFERRED_TYPE)
|
new o.FnParam(EventHandlerVars.event.name !, o.INFERRED_TYPE)
|
||||||
],
|
],
|
||||||
[...preStmts, ...handleEventStmts, new o.ReturnStatement(ALLOW_DEFAULT_VAR)],
|
[...preStmts, ...handleEventStmts, new o.ReturnStatement(ALLOW_DEFAULT_VAR)],
|
||||||
o.INFERRED_TYPE);
|
o.INFERRED_TYPE);
|
||||||
@ -933,9 +934,9 @@ function singleProviderDef(providerType: ProviderAstType, providerMeta: CompileP
|
|||||||
let flags: NodeFlags;
|
let flags: NodeFlags;
|
||||||
let deps: CompileDiDependencyMetadata[];
|
let deps: CompileDiDependencyMetadata[];
|
||||||
if (providerType === ProviderAstType.Directive || providerType === ProviderAstType.Component) {
|
if (providerType === ProviderAstType.Directive || providerType === ProviderAstType.Component) {
|
||||||
providerExpr = o.importExpr(providerMeta.useClass);
|
providerExpr = o.importExpr(providerMeta.useClass !);
|
||||||
flags = NodeFlags.TypeDirective;
|
flags = NodeFlags.TypeDirective;
|
||||||
deps = providerMeta.deps || providerMeta.useClass.diDeps;
|
deps = providerMeta.deps || providerMeta.useClass !.diDeps;
|
||||||
} else {
|
} else {
|
||||||
if (providerMeta.useClass) {
|
if (providerMeta.useClass) {
|
||||||
providerExpr = o.importExpr(providerMeta.useClass);
|
providerExpr = o.importExpr(providerMeta.useClass);
|
||||||
@ -966,7 +967,7 @@ function tokenExpr(tokenMeta: CompileTokenMetadata): o.Expression {
|
|||||||
function depDef(dep: CompileDiDependencyMetadata): o.Expression {
|
function depDef(dep: CompileDiDependencyMetadata): o.Expression {
|
||||||
// Note: the following fields have already been normalized out by provider_analyzer:
|
// Note: the following fields have already been normalized out by provider_analyzer:
|
||||||
// - isAttribute, isSelf, isHost
|
// - isAttribute, isSelf, isHost
|
||||||
const expr = dep.isValue ? convertValueToOutputAst(dep.value) : tokenExpr(dep.token);
|
const expr = dep.isValue ? convertValueToOutputAst(dep.value) : tokenExpr(dep.token !);
|
||||||
let flags = DepFlags.None;
|
let flags = DepFlags.None;
|
||||||
if (dep.isSkipSelf) {
|
if (dep.isSkipSelf) {
|
||||||
flags |= DepFlags.SkipSelf;
|
flags |= DepFlags.SkipSelf;
|
||||||
@ -1110,11 +1111,11 @@ function findStaticQueryIds(
|
|||||||
nodes.forEach((node) => {
|
nodes.forEach((node) => {
|
||||||
const staticQueryIds = new Set<number>();
|
const staticQueryIds = new Set<number>();
|
||||||
const dynamicQueryIds = new Set<number>();
|
const dynamicQueryIds = new Set<number>();
|
||||||
let queryMatches: QueryMatch[];
|
let queryMatches: QueryMatch[] = undefined !;
|
||||||
if (node instanceof ElementAst) {
|
if (node instanceof ElementAst) {
|
||||||
findStaticQueryIds(node.children, result);
|
findStaticQueryIds(node.children, result);
|
||||||
node.children.forEach((child) => {
|
node.children.forEach((child) => {
|
||||||
const childData = result.get(child);
|
const childData = result.get(child) !;
|
||||||
childData.staticQueryIds.forEach(queryId => staticQueryIds.add(queryId));
|
childData.staticQueryIds.forEach(queryId => staticQueryIds.add(queryId));
|
||||||
childData.dynamicQueryIds.forEach(queryId => dynamicQueryIds.add(queryId));
|
childData.dynamicQueryIds.forEach(queryId => dynamicQueryIds.add(queryId));
|
||||||
});
|
});
|
||||||
@ -1122,7 +1123,7 @@ function findStaticQueryIds(
|
|||||||
} else if (node instanceof EmbeddedTemplateAst) {
|
} else if (node instanceof EmbeddedTemplateAst) {
|
||||||
findStaticQueryIds(node.children, result);
|
findStaticQueryIds(node.children, result);
|
||||||
node.children.forEach((child) => {
|
node.children.forEach((child) => {
|
||||||
const childData = result.get(child);
|
const childData = result.get(child) !;
|
||||||
childData.staticQueryIds.forEach(queryId => dynamicQueryIds.add(queryId));
|
childData.staticQueryIds.forEach(queryId => dynamicQueryIds.add(queryId));
|
||||||
childData.dynamicQueryIds.forEach(queryId => dynamicQueryIds.add(queryId));
|
childData.dynamicQueryIds.forEach(queryId => dynamicQueryIds.add(queryId));
|
||||||
});
|
});
|
||||||
@ -1149,7 +1150,7 @@ function staticViewQueryIds(nodeStaticQueryIds: Map<TemplateAst, StaticAndDynami
|
|||||||
return {staticQueryIds, dynamicQueryIds};
|
return {staticQueryIds, dynamicQueryIds};
|
||||||
}
|
}
|
||||||
|
|
||||||
function createComponentFactoryResolver(directives: DirectiveAst[]): ProviderAst {
|
function createComponentFactoryResolver(directives: DirectiveAst[]): ProviderAst|null {
|
||||||
const componentDirMeta = directives.find(dirAst => dirAst.directive.isComponent);
|
const componentDirMeta = directives.find(dirAst => dirAst.directive.isComponent);
|
||||||
if (componentDirMeta && componentDirMeta.directive.entryComponents.length) {
|
if (componentDirMeta && componentDirMeta.directive.entryComponents.length) {
|
||||||
const entryComponentFactories = componentDirMeta.directive.entryComponents.map(
|
const entryComponentFactories = componentDirMeta.directive.entryComponents.map(
|
||||||
@ -1174,7 +1175,7 @@ function createComponentFactoryResolver(directives: DirectiveAst[]): ProviderAst
|
|||||||
}
|
}
|
||||||
|
|
||||||
function elementEventNameAndTarget(
|
function elementEventNameAndTarget(
|
||||||
eventAst: BoundEventAst, dirAst: DirectiveAst): {name: string, target: string} {
|
eventAst: BoundEventAst, dirAst: DirectiveAst | null): {name: string, target: string | null} {
|
||||||
if (eventAst.isAnimation) {
|
if (eventAst.isAnimation) {
|
||||||
return {
|
return {
|
||||||
name: `@${eventAst.name}.${eventAst.phase}`,
|
name: `@${eventAst.name}.${eventAst.phase}`,
|
||||||
|
@ -110,7 +110,8 @@ describe('compiler (unbundled Angular)', () => {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
function findLineAndColumn(file: string, token: string): {line: number, column: number} {
|
function findLineAndColumn(
|
||||||
|
file: string, token: string): {line: number | null, column: number | null} {
|
||||||
const index = file.indexOf(token);
|
const index = file.indexOf(token);
|
||||||
if (index === -1) {
|
if (index === -1) {
|
||||||
return {line: null, column: null};
|
return {line: null, column: null};
|
||||||
@ -178,7 +179,7 @@ describe('compiler (unbundled Angular)', () => {
|
|||||||
appDir['app.component.ts'] = createComponentSource(templateDecorator(template));
|
appDir['app.component.ts'] = createComponentSource(templateDecorator(template));
|
||||||
|
|
||||||
compileApp().then((genFile) => {
|
compileApp().then((genFile) => {
|
||||||
const sourceMap = extractSourceMap(genFile.source);
|
const sourceMap = extractSourceMap(genFile.source) !;
|
||||||
expect(sourceMap.file).toEqual(genFile.genFileUrl);
|
expect(sourceMap.file).toEqual(genFile.genFileUrl);
|
||||||
|
|
||||||
// the generated file contains code that is not mapped to
|
// the generated file contains code that is not mapped to
|
||||||
@ -199,7 +200,7 @@ describe('compiler (unbundled Angular)', () => {
|
|||||||
appDir['app.component.ts'] = createComponentSource(templateDecorator(template));
|
appDir['app.component.ts'] = createComponentSource(templateDecorator(template));
|
||||||
|
|
||||||
compileApp().then((genFile) => {
|
compileApp().then((genFile) => {
|
||||||
const sourceMap = extractSourceMap(genFile.source);
|
const sourceMap = extractSourceMap(genFile.source) !;
|
||||||
expect(originalPositionFor(sourceMap, findLineAndColumn(genFile.source, `'span'`)))
|
expect(originalPositionFor(sourceMap, findLineAndColumn(genFile.source, `'span'`)))
|
||||||
.toEqual({line: 2, column: 3, source: ngUrl});
|
.toEqual({line: 2, column: 3, source: ngUrl});
|
||||||
});
|
});
|
||||||
@ -211,7 +212,7 @@ describe('compiler (unbundled Angular)', () => {
|
|||||||
appDir['app.component.ts'] = createComponentSource(templateDecorator(template));
|
appDir['app.component.ts'] = createComponentSource(templateDecorator(template));
|
||||||
|
|
||||||
compileApp().then((genFile) => {
|
compileApp().then((genFile) => {
|
||||||
const sourceMap = extractSourceMap(genFile.source);
|
const sourceMap = extractSourceMap(genFile.source) !;
|
||||||
expect(
|
expect(
|
||||||
originalPositionFor(sourceMap, findLineAndColumn(genFile.source, `someMethod()`)))
|
originalPositionFor(sourceMap, findLineAndColumn(genFile.source, `someMethod()`)))
|
||||||
.toEqual({line: 2, column: 9, source: ngUrl});
|
.toEqual({line: 2, column: 9, source: ngUrl});
|
||||||
@ -224,7 +225,7 @@ describe('compiler (unbundled Angular)', () => {
|
|||||||
appDir['app.component.ts'] = createComponentSource(templateDecorator(template));
|
appDir['app.component.ts'] = createComponentSource(templateDecorator(template));
|
||||||
|
|
||||||
compileApp().then((genFile) => {
|
compileApp().then((genFile) => {
|
||||||
const sourceMap = extractSourceMap(genFile.source);
|
const sourceMap = extractSourceMap(genFile.source) !;
|
||||||
expect(
|
expect(
|
||||||
originalPositionFor(sourceMap, findLineAndColumn(genFile.source, `someMethod()`)))
|
originalPositionFor(sourceMap, findLineAndColumn(genFile.source, `someMethod()`)))
|
||||||
.toEqual({line: 2, column: 9, source: ngUrl});
|
.toEqual({line: 2, column: 9, source: ngUrl});
|
||||||
@ -235,7 +236,7 @@ describe('compiler (unbundled Angular)', () => {
|
|||||||
appDir['app.component.ts'] = createComponentSource(templateDecorator('Hello World!'));
|
appDir['app.component.ts'] = createComponentSource(templateDecorator('Hello World!'));
|
||||||
|
|
||||||
compileApp().then((genFile) => {
|
compileApp().then((genFile) => {
|
||||||
const sourceMap = extractSourceMap(genFile.source);
|
const sourceMap = extractSourceMap(genFile.source) !;
|
||||||
expect(originalPositionFor(sourceMap, {line: 1, column: 0}))
|
expect(originalPositionFor(sourceMap, {line: 1, column: 0}))
|
||||||
.toEqual({line: 1, column: 0, source: ngComponentPath});
|
.toEqual({line: 1, column: 0, source: ngComponentPath});
|
||||||
});
|
});
|
||||||
@ -328,7 +329,7 @@ describe('compiler (unbundled Angular)', () => {
|
|||||||
compile(host, aotHost, expectNoDiagnostics).then((generatedFiles) => {
|
compile(host, aotHost, expectNoDiagnostics).then((generatedFiles) => {
|
||||||
const genFile = generatedFiles.find(genFile => genFile.srcFileUrl === '/app/app.ts');
|
const genFile = generatedFiles.find(genFile => genFile.srcFileUrl === '/app/app.ts');
|
||||||
const createComponentFactoryCall =
|
const createComponentFactoryCall =
|
||||||
/ɵccf\([^)]*\)/m.exec(genFile.source)[0].replace(/\s*/g, '');
|
/ɵccf\([^)]*\)/m.exec(genFile.source) ![0].replace(/\s*/g, '');
|
||||||
// selector
|
// selector
|
||||||
expect(createComponentFactoryCall).toContain('my-comp');
|
expect(createComponentFactoryCall).toContain('my-comp');
|
||||||
// inputs
|
// inputs
|
||||||
|
@ -360,7 +360,7 @@ describe('StaticReflector', () => {
|
|||||||
it('should record data about the error in the exception', () => {
|
it('should record data about the error in the exception', () => {
|
||||||
let threw = false;
|
let threw = false;
|
||||||
try {
|
try {
|
||||||
const metadata = host.getMetadataFor('/tmp/src/invalid-metadata.ts');
|
const metadata = host.getMetadataFor('/tmp/src/invalid-metadata.ts') !;
|
||||||
expect(metadata).toBeDefined();
|
expect(metadata).toBeDefined();
|
||||||
const moduleMetadata: any = metadata[0]['metadata'];
|
const moduleMetadata: any = metadata[0]['metadata'];
|
||||||
expect(moduleMetadata).toBeDefined();
|
expect(moduleMetadata).toBeDefined();
|
||||||
|
@ -382,7 +382,7 @@ export class MockSummaryResolver implements SummaryResolver<StaticSymbol> {
|
|||||||
}
|
}
|
||||||
getImportAs(symbol: StaticSymbol): StaticSymbol {
|
getImportAs(symbol: StaticSymbol): StaticSymbol {
|
||||||
const entry = this.importAs.find(entry => entry.symbol === symbol);
|
const entry = this.importAs.find(entry => entry.symbol === symbol);
|
||||||
return entry ? entry.importAs : undefined;
|
return entry ? entry.importAs : undefined !;
|
||||||
}
|
}
|
||||||
|
|
||||||
isLibraryFile(filePath: string): boolean { return filePath.endsWith('.d.ts'); }
|
isLibraryFile(filePath: string): boolean { return filePath.endsWith('.d.ts'); }
|
||||||
@ -429,7 +429,7 @@ export class MockStaticSymbolResolverHost implements StaticSymbolResolverHost {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (modulePath.indexOf('.') === 0) {
|
if (modulePath.indexOf('.') === 0) {
|
||||||
const baseName = pathTo(containingFile, modulePath);
|
const baseName = pathTo(containingFile !, modulePath);
|
||||||
const tsName = baseName + '.ts';
|
const tsName = baseName + '.ts';
|
||||||
if (this._getMetadataFor(tsName)) {
|
if (this._getMetadataFor(tsName)) {
|
||||||
return tsName;
|
return tsName;
|
||||||
|
@ -95,7 +95,7 @@ export function main() {
|
|||||||
members: {aMethod: {__symbolic: 'function'}},
|
members: {aMethod: {__symbolic: 'function'}},
|
||||||
statics: {aStatic: true}
|
statics: {aStatic: true}
|
||||||
});
|
});
|
||||||
expect(summaries[1].type.type.reference)
|
expect(summaries[1].type !.type.reference)
|
||||||
.toBe(symbolCache.get('/tmp/some_service.d.ts', 'SomeService'));
|
.toBe(symbolCache.get('/tmp/some_service.d.ts', 'SomeService'));
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -203,7 +203,7 @@ export function main() {
|
|||||||
expect(summaries[2].metadata).toEqual('b');
|
expect(summaries[2].metadata).toEqual('b');
|
||||||
// SomService is a transitive dep, but should have been serialized as well.
|
// SomService is a transitive dep, but should have been serialized as well.
|
||||||
expect(summaries[3].symbol).toBe(symbolCache.get('/tmp/external_svc.d.ts', 'SomeService'));
|
expect(summaries[3].symbol).toBe(symbolCache.get('/tmp/external_svc.d.ts', 'SomeService'));
|
||||||
expect(summaries[3].type.type.reference)
|
expect(summaries[3].type !.type.reference)
|
||||||
.toBe(symbolCache.get('/tmp/external_svc.d.ts', 'SomeService'));
|
.toBe(symbolCache.get('/tmp/external_svc.d.ts', 'SomeService'));
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -18,7 +18,7 @@ export type MockDirectory = {
|
|||||||
[name: string]: MockData | undefined;
|
[name: string]: MockData | undefined;
|
||||||
};
|
};
|
||||||
|
|
||||||
export function isDirectory(data: MockData): data is MockDirectory {
|
export function isDirectory(data: MockData | undefined): data is MockDirectory {
|
||||||
return typeof data !== 'string';
|
return typeof data !== 'string';
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -146,6 +146,7 @@ export class EmittingCompilerHost implements ts.CompilerHost {
|
|||||||
if (content) {
|
if (content) {
|
||||||
return ts.createSourceFile(fileName, content, languageVersion, /* setParentNodes */ true);
|
return ts.createSourceFile(fileName, content, languageVersion, /* setParentNodes */ true);
|
||||||
}
|
}
|
||||||
|
throw new Error(`File not found '${fileName}'.`);
|
||||||
}
|
}
|
||||||
|
|
||||||
getDefaultLibFileName(options: ts.CompilerOptions): string { return 'lib.d.ts'; }
|
getDefaultLibFileName(options: ts.CompilerOptions): string { return 'lib.d.ts'; }
|
||||||
@ -235,7 +236,7 @@ export class MockCompilerHost implements ts.CompilerHost {
|
|||||||
let result = open(fileName, this.data) != null;
|
let result = open(fileName, this.data) != null;
|
||||||
if (!result && fileName.startsWith(MOCK_NODEMODULES_PREFIX)) {
|
if (!result && fileName.startsWith(MOCK_NODEMODULES_PREFIX)) {
|
||||||
const libraryPath = fileName.substr(MOCK_NODEMODULES_PREFIX.length - 1);
|
const libraryPath = fileName.substr(MOCK_NODEMODULES_PREFIX.length - 1);
|
||||||
for (const library of this.libraries) {
|
for (const library of this.libraries !) {
|
||||||
if (library.has(libraryPath)) {
|
if (library.has(libraryPath)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -252,7 +253,7 @@ export class MockCompilerHost implements ts.CompilerHost {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
readFile(fileName: string): string { return this.getFileContent(fileName); }
|
readFile(fileName: string): string { return this.getFileContent(fileName) !; }
|
||||||
|
|
||||||
trace(s: string): void { this.traces.push(s); }
|
trace(s: string): void { this.traces.push(s); }
|
||||||
|
|
||||||
@ -265,10 +266,8 @@ export class MockCompilerHost implements ts.CompilerHost {
|
|||||||
if (isDirectory(data)) {
|
if (isDirectory(data)) {
|
||||||
return Object.keys(data).filter(k => isDirectory(data[k]));
|
return Object.keys(data).filter(k => isDirectory(data[k]));
|
||||||
}
|
}
|
||||||
return [];
|
|
||||||
} else {
|
|
||||||
return undefined;
|
|
||||||
}
|
}
|
||||||
|
return [];
|
||||||
}
|
}
|
||||||
|
|
||||||
// ts.CompilerHost
|
// ts.CompilerHost
|
||||||
@ -283,7 +282,7 @@ export class MockCompilerHost implements ts.CompilerHost {
|
|||||||
this.sourceFiles.set(fileName, result);
|
this.sourceFiles.set(fileName, result);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return result;
|
return result !;
|
||||||
}
|
}
|
||||||
|
|
||||||
getDefaultLibFileName(options: ts.CompilerOptions): string { return 'lib.d.ts'; }
|
getDefaultLibFileName(options: ts.CompilerOptions): string { return 'lib.d.ts'; }
|
||||||
@ -318,7 +317,7 @@ export class MockCompilerHost implements ts.CompilerHost {
|
|||||||
const result = open(fileName, this.data);
|
const result = open(fileName, this.data);
|
||||||
if (!result && fileName.startsWith(MOCK_NODEMODULES_PREFIX)) {
|
if (!result && fileName.startsWith(MOCK_NODEMODULES_PREFIX)) {
|
||||||
const libraryPath = fileName.substr(MOCK_NODEMODULES_PREFIX.length - 1);
|
const libraryPath = fileName.substr(MOCK_NODEMODULES_PREFIX.length - 1);
|
||||||
for (const library of this.libraries) {
|
for (const library of this.libraries !) {
|
||||||
if (library.has(libraryPath)) return library.get(libraryPath);
|
if (library.has(libraryPath)) return library.get(libraryPath);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -367,9 +366,9 @@ export class MockAotCompilerHost implements AotCompilerHost {
|
|||||||
tsFilesOnly() { this.dtsAreSource = false; }
|
tsFilesOnly() { this.dtsAreSource = false; }
|
||||||
|
|
||||||
// StaticSymbolResolverHost
|
// StaticSymbolResolverHost
|
||||||
getMetadataFor(modulePath: string): {[key: string]: any}[] {
|
getMetadataFor(modulePath: string): {[key: string]: any}[]|null {
|
||||||
if (!this.tsHost.fileExists(modulePath)) {
|
if (!this.tsHost.fileExists(modulePath)) {
|
||||||
return undefined;
|
return null;
|
||||||
}
|
}
|
||||||
if (DTS.test(modulePath)) {
|
if (DTS.test(modulePath)) {
|
||||||
if (this.metadataVisible) {
|
if (this.metadataVisible) {
|
||||||
@ -384,6 +383,7 @@ export class MockAotCompilerHost implements AotCompilerHost {
|
|||||||
const metadata = this.metadataCollector.getMetadata(sf);
|
const metadata = this.metadataCollector.getMetadata(sf);
|
||||||
return metadata ? [metadata] : [];
|
return metadata ? [metadata] : [];
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
moduleNameToFileName(moduleName: string, containingFile: string): string|null {
|
moduleNameToFileName(moduleName: string, containingFile: string): string|null {
|
||||||
@ -439,11 +439,11 @@ export class MockMetadataBundlerHost implements MetadataBundlerHost {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function find(fileName: string, data: MockData): MockData|undefined {
|
function find(fileName: string, data: MockData | undefined): MockData|undefined {
|
||||||
if (!data) return undefined;
|
if (!data) return undefined;
|
||||||
let names = fileName.split('/');
|
let names = fileName.split('/');
|
||||||
if (names.length && !names[0].length) names.shift();
|
if (names.length && !names[0].length) names.shift();
|
||||||
let current = data;
|
let current: MockData|undefined = data;
|
||||||
for (let name of names) {
|
for (let name of names) {
|
||||||
if (typeof current === 'string')
|
if (typeof current === 'string')
|
||||||
return undefined;
|
return undefined;
|
||||||
@ -454,7 +454,7 @@ function find(fileName: string, data: MockData): MockData|undefined {
|
|||||||
return current;
|
return current;
|
||||||
}
|
}
|
||||||
|
|
||||||
function open(fileName: string, data: MockData): string|undefined {
|
function open(fileName: string, data: MockData | undefined): string|undefined {
|
||||||
let result = find(fileName, data);
|
let result = find(fileName, data);
|
||||||
if (typeof result === 'string') {
|
if (typeof result === 'string') {
|
||||||
return result;
|
return result;
|
||||||
@ -462,7 +462,7 @@ function open(fileName: string, data: MockData): string|undefined {
|
|||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
function directoryExists(dirname: string, data: MockData): boolean {
|
function directoryExists(dirname: string, data: MockData | undefined): boolean {
|
||||||
let result = find(dirname, data);
|
let result = find(dirname, data);
|
||||||
return result && typeof result !== 'string';
|
return !!result && typeof result !== 'string';
|
||||||
}
|
}
|
||||||
|
@ -274,7 +274,7 @@ export function main() {
|
|||||||
it('should throw an error if a selector is being parsed while in the wrong mode', () => {
|
it('should throw an error if a selector is being parsed while in the wrong mode', () => {
|
||||||
const cssCode = '.class > tag';
|
const cssCode = '.class > tag';
|
||||||
|
|
||||||
let capturedMessage: string;
|
let capturedMessage: string = undefined !;
|
||||||
try {
|
try {
|
||||||
tokenize(cssCode, false, CssLexerMode.STYLE_BLOCK);
|
tokenize(cssCode, false, CssLexerMode.STYLE_BLOCK);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
@ -282,7 +282,7 @@ export function main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
expect(capturedMessage).toMatch(/Unexpected character \[\>\] at column 0:7 in expression/g);
|
expect(capturedMessage).toMatch(/Unexpected character \[\>\] at column 0:7 in expression/g);
|
||||||
capturedMessage = null;
|
capturedMessage = null !;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
tokenize(cssCode, false, CssLexerMode.SELECTOR);
|
tokenize(cssCode, false, CssLexerMode.SELECTOR);
|
||||||
|
@ -111,26 +111,26 @@ export function main() {
|
|||||||
expect(ast.rules.length).toEqual(1);
|
expect(ast.rules.length).toEqual(1);
|
||||||
|
|
||||||
const rule = <CssKeyframeRuleAst>ast.rules[0];
|
const rule = <CssKeyframeRuleAst>ast.rules[0];
|
||||||
expect(rule.name.strValue).toEqual('rotateMe');
|
expect(rule.name !.strValue).toEqual('rotateMe');
|
||||||
|
|
||||||
const block = <CssBlockAst>rule.block;
|
const block = <CssBlockAst>rule.block;
|
||||||
const fromRule = <CssKeyframeDefinitionAst>block.entries[0];
|
const fromRule = <CssKeyframeDefinitionAst>block.entries[0];
|
||||||
|
|
||||||
expect(fromRule.name.strValue).toEqual('from');
|
expect(fromRule.name !.strValue).toEqual('from');
|
||||||
const fromStyle = <CssDefinitionAst>(<CssBlockAst>fromRule.block).entries[0];
|
const fromStyle = <CssDefinitionAst>(<CssBlockAst>fromRule.block).entries[0];
|
||||||
expect(fromStyle.property.strValue).toEqual('transform');
|
expect(fromStyle.property.strValue).toEqual('transform');
|
||||||
assertTokens(fromStyle.value.tokens, ['rotate', '(', '-360', 'deg', ')']);
|
assertTokens(fromStyle.value.tokens, ['rotate', '(', '-360', 'deg', ')']);
|
||||||
|
|
||||||
const midRule = <CssKeyframeDefinitionAst>block.entries[1];
|
const midRule = <CssKeyframeDefinitionAst>block.entries[1];
|
||||||
|
|
||||||
expect(midRule.name.strValue).toEqual('50%');
|
expect(midRule.name !.strValue).toEqual('50%');
|
||||||
const midStyle = <CssDefinitionAst>(<CssBlockAst>midRule.block).entries[0];
|
const midStyle = <CssDefinitionAst>(<CssBlockAst>midRule.block).entries[0];
|
||||||
expect(midStyle.property.strValue).toEqual('transform');
|
expect(midStyle.property.strValue).toEqual('transform');
|
||||||
assertTokens(midStyle.value.tokens, ['rotate', '(', '0', 'deg', ')']);
|
assertTokens(midStyle.value.tokens, ['rotate', '(', '0', 'deg', ')']);
|
||||||
|
|
||||||
const toRule = <CssKeyframeDefinitionAst>block.entries[2];
|
const toRule = <CssKeyframeDefinitionAst>block.entries[2];
|
||||||
|
|
||||||
expect(toRule.name.strValue).toEqual('to');
|
expect(toRule.name !.strValue).toEqual('to');
|
||||||
const toStyle = <CssDefinitionAst>(<CssBlockAst>toRule.block).entries[0];
|
const toStyle = <CssDefinitionAst>(<CssBlockAst>toRule.block).entries[0];
|
||||||
expect(toStyle.property.strValue).toEqual('transform');
|
expect(toStyle.property.strValue).toEqual('transform');
|
||||||
assertTokens(toStyle.value.tokens, ['rotate', '(', '360', 'deg', ')']);
|
assertTokens(toStyle.value.tokens, ['rotate', '(', '360', 'deg', ')']);
|
||||||
@ -695,7 +695,7 @@ export function main() {
|
|||||||
const ast = output.ast;
|
const ast = output.ast;
|
||||||
|
|
||||||
assertMatchesOffsetAndChar(ast.location.start, 0, '#');
|
assertMatchesOffsetAndChar(ast.location.start, 0, '#');
|
||||||
assertMatchesOffsetAndChar(ast.location.end, 22, undefined);
|
assertMatchesOffsetAndChar(ast.location.end, 22, undefined !);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -257,7 +257,7 @@ export function main() {
|
|||||||
expect(captures.length).toEqual(1);
|
expect(captures.length).toEqual(1);
|
||||||
|
|
||||||
const keyframe1 = <CssKeyframeRuleAst>_getCaptureAst(captures, 0);
|
const keyframe1 = <CssKeyframeRuleAst>_getCaptureAst(captures, 0);
|
||||||
expect(keyframe1.name.strValue).toEqual('rotate');
|
expect(keyframe1.name !.strValue).toEqual('rotate');
|
||||||
expect(keyframe1.block.entries.length).toEqual(2);
|
expect(keyframe1.block.entries.length).toEqual(2);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -5,6 +5,7 @@
|
|||||||
* Use of this source code is governed by an MIT-style license that can be
|
* Use of this source code is governed by an MIT-style license that can be
|
||||||
* found in the LICENSE file at https://angular.io/license
|
* found in the LICENSE file at https://angular.io/license
|
||||||
*/
|
*/
|
||||||
|
import {CompileAnimationEntryMetadata} from '@angular/compiler';
|
||||||
import {CompileDirectiveMetadata, CompileStylesheetMetadata, CompileTemplateMetadata, CompileTypeMetadata} from '@angular/compiler/src/compile_metadata';
|
import {CompileDirectiveMetadata, CompileStylesheetMetadata, CompileTemplateMetadata, CompileTypeMetadata} from '@angular/compiler/src/compile_metadata';
|
||||||
import {CompilerConfig} from '@angular/compiler/src/config';
|
import {CompilerConfig} from '@angular/compiler/src/config';
|
||||||
import {DirectiveNormalizer} from '@angular/compiler/src/directive_normalizer';
|
import {DirectiveNormalizer} from '@angular/compiler/src/directive_normalizer';
|
||||||
@ -15,11 +16,137 @@ import {ViewEncapsulation} from '@angular/core/src/metadata/view';
|
|||||||
import {TestBed} from '@angular/core/testing';
|
import {TestBed} from '@angular/core/testing';
|
||||||
import {AsyncTestCompleter, beforeEach, describe, expect, inject, it} from '@angular/core/testing/src/testing_internal';
|
import {AsyncTestCompleter, beforeEach, describe, expect, inject, it} from '@angular/core/testing/src/testing_internal';
|
||||||
|
|
||||||
|
import {SyncAsyncResult, noUndefined} from '../src/util';
|
||||||
|
|
||||||
import {SpyResourceLoader} from './spies';
|
import {SpyResourceLoader} from './spies';
|
||||||
|
|
||||||
const SOME_MODULE_URL = 'package:some/module/a.js';
|
const SOME_MODULE_URL = 'package:some/module/a.js';
|
||||||
const SOME_HTTP_MODULE_URL = 'http://some/module/a.js';
|
const SOME_HTTP_MODULE_URL = 'http://some/module/a.js';
|
||||||
|
|
||||||
|
function normalizeTemplate(normalizer: DirectiveNormalizer, o: {
|
||||||
|
ngModuleType?: any; componentType?: any; moduleUrl?: string; template?: string | null;
|
||||||
|
templateUrl?: string | null;
|
||||||
|
styles?: string[];
|
||||||
|
styleUrls?: string[];
|
||||||
|
interpolation?: [string, string] | null;
|
||||||
|
encapsulation?: ViewEncapsulation | null;
|
||||||
|
animations?: CompileAnimationEntryMetadata[];
|
||||||
|
}) {
|
||||||
|
return normalizer.normalizeTemplate({
|
||||||
|
ngModuleType: noUndefined(o.ngModuleType),
|
||||||
|
componentType: noUndefined(o.componentType),
|
||||||
|
moduleUrl: noUndefined(o.moduleUrl),
|
||||||
|
template: noUndefined(o.template),
|
||||||
|
templateUrl: noUndefined(o.templateUrl),
|
||||||
|
styles: noUndefined(o.styles),
|
||||||
|
styleUrls: noUndefined(o.styleUrls),
|
||||||
|
interpolation: noUndefined(o.interpolation),
|
||||||
|
encapsulation: noUndefined(o.encapsulation),
|
||||||
|
animations: noUndefined(o.animations)
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function normalizeTemplateAsync(normalizer: DirectiveNormalizer, o: {
|
||||||
|
ngModuleType?: any; componentType?: any; moduleUrl?: string; template?: string | null;
|
||||||
|
templateUrl?: string | null;
|
||||||
|
styles?: string[];
|
||||||
|
styleUrls?: string[];
|
||||||
|
interpolation?: [string, string] | null;
|
||||||
|
encapsulation?: ViewEncapsulation | null;
|
||||||
|
animations?: CompileAnimationEntryMetadata[];
|
||||||
|
}) {
|
||||||
|
return normalizer.normalizeTemplateAsync({
|
||||||
|
ngModuleType: noUndefined(o.ngModuleType),
|
||||||
|
componentType: noUndefined(o.componentType),
|
||||||
|
moduleUrl: noUndefined(o.moduleUrl),
|
||||||
|
template: noUndefined(o.template),
|
||||||
|
templateUrl: noUndefined(o.templateUrl),
|
||||||
|
styles: noUndefined(o.styles),
|
||||||
|
styleUrls: noUndefined(o.styleUrls),
|
||||||
|
interpolation: noUndefined(o.interpolation),
|
||||||
|
encapsulation: noUndefined(o.encapsulation),
|
||||||
|
animations: noUndefined(o.animations)
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function normalizeTemplateSync(normalizer: DirectiveNormalizer, o: {
|
||||||
|
ngModuleType?: any; componentType?: any; moduleUrl?: string; template?: string | null;
|
||||||
|
templateUrl?: string | null;
|
||||||
|
styles?: string[];
|
||||||
|
styleUrls?: string[];
|
||||||
|
interpolation?: [string, string] | null;
|
||||||
|
encapsulation?: ViewEncapsulation | null;
|
||||||
|
animations?: CompileAnimationEntryMetadata[];
|
||||||
|
}): CompileTemplateMetadata {
|
||||||
|
return normalizer.normalizeTemplateSync({
|
||||||
|
ngModuleType: noUndefined(o.ngModuleType),
|
||||||
|
componentType: noUndefined(o.componentType),
|
||||||
|
moduleUrl: noUndefined(o.moduleUrl),
|
||||||
|
template: noUndefined(o.template),
|
||||||
|
templateUrl: noUndefined(o.templateUrl),
|
||||||
|
styles: noUndefined(o.styles),
|
||||||
|
styleUrls: noUndefined(o.styleUrls),
|
||||||
|
interpolation: noUndefined(o.interpolation),
|
||||||
|
encapsulation: noUndefined(o.encapsulation),
|
||||||
|
animations: noUndefined(o.animations)
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function compileTemplateMetadata({encapsulation, template, templateUrl, styles, styleUrls,
|
||||||
|
externalStylesheets, animations, ngContentSelectors,
|
||||||
|
interpolation, isInline}: {
|
||||||
|
encapsulation?: ViewEncapsulation | null,
|
||||||
|
template?: string | null,
|
||||||
|
templateUrl?: string | null,
|
||||||
|
styles?: string[],
|
||||||
|
styleUrls?: string[],
|
||||||
|
externalStylesheets?: CompileStylesheetMetadata[],
|
||||||
|
ngContentSelectors?: string[],
|
||||||
|
animations?: any[],
|
||||||
|
interpolation?: [string, string] | null,
|
||||||
|
isInline?: boolean
|
||||||
|
}): CompileTemplateMetadata {
|
||||||
|
return new CompileTemplateMetadata({
|
||||||
|
encapsulation: encapsulation || null,
|
||||||
|
template: template || null,
|
||||||
|
templateUrl: templateUrl || null,
|
||||||
|
styles: styles || [],
|
||||||
|
styleUrls: styleUrls || [],
|
||||||
|
externalStylesheets: externalStylesheets || [],
|
||||||
|
ngContentSelectors: ngContentSelectors || [],
|
||||||
|
animations: animations || [],
|
||||||
|
interpolation: interpolation || null,
|
||||||
|
isInline: !!isInline,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function normalizeLoadedTemplate(
|
||||||
|
normalizer: DirectiveNormalizer, o: {
|
||||||
|
ngModuleType?: any; componentType?: any; moduleUrl?: string; template?: string | null;
|
||||||
|
templateUrl?: string | null;
|
||||||
|
styles?: string[];
|
||||||
|
styleUrls?: string[];
|
||||||
|
interpolation?: [string, string] | null;
|
||||||
|
encapsulation?: ViewEncapsulation | null;
|
||||||
|
animations?: CompileAnimationEntryMetadata[];
|
||||||
|
},
|
||||||
|
template: string, templateAbsUrl: string) {
|
||||||
|
return normalizer.normalizeLoadedTemplate(
|
||||||
|
{
|
||||||
|
ngModuleType: o.ngModuleType || null,
|
||||||
|
componentType: o.componentType || null,
|
||||||
|
moduleUrl: o.moduleUrl || '',
|
||||||
|
template: o.template || null,
|
||||||
|
templateUrl: o.templateUrl || null,
|
||||||
|
styles: o.styles || [],
|
||||||
|
styleUrls: o.styleUrls || [],
|
||||||
|
interpolation: o.interpolation || null,
|
||||||
|
encapsulation: o.encapsulation || null,
|
||||||
|
animations: o.animations || null,
|
||||||
|
},
|
||||||
|
template, templateAbsUrl);
|
||||||
|
}
|
||||||
|
|
||||||
export function main() {
|
export function main() {
|
||||||
describe('DirectiveNormalizer', () => {
|
describe('DirectiveNormalizer', () => {
|
||||||
beforeEach(() => { TestBed.configureCompiler({providers: TEST_COMPILER_PROVIDERS}); });
|
beforeEach(() => { TestBed.configureCompiler({providers: TEST_COMPILER_PROVIDERS}); });
|
||||||
@ -27,46 +154,50 @@ export function main() {
|
|||||||
describe('normalizeDirective', () => {
|
describe('normalizeDirective', () => {
|
||||||
it('should throw if no template was specified',
|
it('should throw if no template was specified',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
expect(() => normalizer.normalizeTemplate({
|
expect(() => normalizeTemplate(normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
})).toThrowError('No template specified for component SomeComp');
|
}))
|
||||||
|
.toThrowError('No template specified for component SomeComp');
|
||||||
}));
|
}));
|
||||||
it('should throw if template is not a string',
|
it('should throw if template is not a string',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
expect(() => normalizer.normalizeTemplate({
|
expect(() => normalizeTemplate(normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
template: <any>{}
|
template: <any>{}
|
||||||
})).toThrowError('The template specified for component SomeComp is not a string');
|
}))
|
||||||
|
.toThrowError('The template specified for component SomeComp is not a string');
|
||||||
}));
|
}));
|
||||||
it('should throw if templateUrl is not a string',
|
it('should throw if templateUrl is not a string',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
expect(() => normalizer.normalizeTemplate({
|
expect(() => normalizeTemplate(normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
templateUrl: <any>{}
|
templateUrl: <any>{}
|
||||||
})).toThrowError('The templateUrl specified for component SomeComp is not a string');
|
}))
|
||||||
|
.toThrowError('The templateUrl specified for component SomeComp is not a string');
|
||||||
}));
|
}));
|
||||||
it('should throw if both template and templateUrl are defined',
|
it('should throw if both template and templateUrl are defined',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
expect(() => normalizer.normalizeTemplate({
|
expect(() => normalizeTemplate(normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
template: '',
|
template: '',
|
||||||
templateUrl: '',
|
templateUrl: '',
|
||||||
})).toThrowError(`'SomeComp' component cannot define both template and templateUrl`);
|
}))
|
||||||
|
.toThrowError(`'SomeComp' component cannot define both template and templateUrl`);
|
||||||
}));
|
}));
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('normalizeTemplateSync', () => {
|
describe('normalizeTemplateSync', () => {
|
||||||
it('should store the template',
|
it('should store the template',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeTemplateSync({
|
const template = normalizeTemplateSync(normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -83,7 +214,7 @@ export function main() {
|
|||||||
|
|
||||||
it('should resolve styles on the annotation against the moduleUrl',
|
it('should resolve styles on the annotation against the moduleUrl',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeTemplateSync({
|
const template = normalizeTemplateSync(normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -98,7 +229,7 @@ export function main() {
|
|||||||
|
|
||||||
it('should resolve styles in the template against the moduleUrl',
|
it('should resolve styles in the template against the moduleUrl',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeTemplateSync({
|
const template = normalizeTemplateSync(normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -113,7 +244,7 @@ export function main() {
|
|||||||
|
|
||||||
it('should use ViewEncapsulation.Emulated by default',
|
it('should use ViewEncapsulation.Emulated by default',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeTemplateSync({
|
const template = normalizeTemplateSync(normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -131,13 +262,13 @@ export function main() {
|
|||||||
[CompilerConfig, DirectiveNormalizer],
|
[CompilerConfig, DirectiveNormalizer],
|
||||||
(config: CompilerConfig, normalizer: DirectiveNormalizer) => {
|
(config: CompilerConfig, normalizer: DirectiveNormalizer) => {
|
||||||
config.defaultEncapsulation = ViewEncapsulation.None;
|
config.defaultEncapsulation = ViewEncapsulation.None;
|
||||||
const template = normalizer.normalizeTemplateSync({
|
const template = normalizeTemplateSync(normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
encapsulation: null,
|
encapsulation: undefined,
|
||||||
template: '',
|
template: '',
|
||||||
templateUrl: null,
|
templateUrl: undefined,
|
||||||
styles: [],
|
styles: [],
|
||||||
styleUrls: ['test.css']
|
styleUrls: ['test.css']
|
||||||
});
|
});
|
||||||
@ -153,23 +284,21 @@ export function main() {
|
|||||||
(async: AsyncTestCompleter, normalizer: DirectiveNormalizer,
|
(async: AsyncTestCompleter, normalizer: DirectiveNormalizer,
|
||||||
resourceLoader: MockResourceLoader) => {
|
resourceLoader: MockResourceLoader) => {
|
||||||
resourceLoader.expect('package:some/module/sometplurl.html', 'a');
|
resourceLoader.expect('package:some/module/sometplurl.html', 'a');
|
||||||
normalizer
|
normalizeTemplateAsync(normalizer, {
|
||||||
.normalizeTemplateAsync({
|
ngModuleType: null,
|
||||||
ngModuleType: null,
|
componentType: SomeComp,
|
||||||
componentType: SomeComp,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
encapsulation: null,
|
||||||
encapsulation: null,
|
template: null,
|
||||||
template: null,
|
templateUrl: 'sometplurl.html',
|
||||||
templateUrl: 'sometplurl.html',
|
styles: [],
|
||||||
styles: [],
|
styleUrls: ['test.css']
|
||||||
styleUrls: ['test.css']
|
}).then((template: CompileTemplateMetadata) => {
|
||||||
})
|
expect(template.template).toEqual('a');
|
||||||
.then((template: CompileTemplateMetadata) => {
|
expect(template.templateUrl).toEqual('package:some/module/sometplurl.html');
|
||||||
expect(template.template).toEqual('a');
|
expect(template.isInline).toBe(false);
|
||||||
expect(template.templateUrl).toEqual('package:some/module/sometplurl.html');
|
async.done();
|
||||||
expect(template.isInline).toBe(false);
|
});
|
||||||
async.done();
|
|
||||||
});
|
|
||||||
resourceLoader.flush();
|
resourceLoader.flush();
|
||||||
}));
|
}));
|
||||||
|
|
||||||
@ -179,21 +308,19 @@ export function main() {
|
|||||||
(async: AsyncTestCompleter, normalizer: DirectiveNormalizer,
|
(async: AsyncTestCompleter, normalizer: DirectiveNormalizer,
|
||||||
resourceLoader: MockResourceLoader) => {
|
resourceLoader: MockResourceLoader) => {
|
||||||
resourceLoader.expect('package:some/module/tpl/sometplurl.html', '');
|
resourceLoader.expect('package:some/module/tpl/sometplurl.html', '');
|
||||||
normalizer
|
normalizeTemplateAsync(normalizer, {
|
||||||
.normalizeTemplateAsync({
|
ngModuleType: null,
|
||||||
ngModuleType: null,
|
componentType: SomeComp,
|
||||||
componentType: SomeComp,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
encapsulation: null,
|
||||||
encapsulation: null,
|
template: null,
|
||||||
template: null,
|
templateUrl: 'tpl/sometplurl.html',
|
||||||
templateUrl: 'tpl/sometplurl.html',
|
styles: [],
|
||||||
styles: [],
|
styleUrls: ['test.css']
|
||||||
styleUrls: ['test.css']
|
}).then((template: CompileTemplateMetadata) => {
|
||||||
})
|
expect(template.styleUrls).toEqual(['package:some/module/test.css']);
|
||||||
.then((template: CompileTemplateMetadata) => {
|
async.done();
|
||||||
expect(template.styleUrls).toEqual(['package:some/module/test.css']);
|
});
|
||||||
async.done();
|
|
||||||
});
|
|
||||||
resourceLoader.flush();
|
resourceLoader.flush();
|
||||||
}));
|
}));
|
||||||
|
|
||||||
@ -204,21 +331,19 @@ export function main() {
|
|||||||
resourceLoader: MockResourceLoader) => {
|
resourceLoader: MockResourceLoader) => {
|
||||||
resourceLoader.expect(
|
resourceLoader.expect(
|
||||||
'package:some/module/tpl/sometplurl.html', '<style>@import test.css</style>');
|
'package:some/module/tpl/sometplurl.html', '<style>@import test.css</style>');
|
||||||
normalizer
|
normalizeTemplateAsync(normalizer, {
|
||||||
.normalizeTemplateAsync({
|
ngModuleType: null,
|
||||||
ngModuleType: null,
|
componentType: SomeComp,
|
||||||
componentType: SomeComp,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
encapsulation: null,
|
||||||
encapsulation: null,
|
template: null,
|
||||||
template: null,
|
templateUrl: 'tpl/sometplurl.html',
|
||||||
templateUrl: 'tpl/sometplurl.html',
|
styles: [],
|
||||||
styles: [],
|
styleUrls: []
|
||||||
styleUrls: []
|
}).then((template: CompileTemplateMetadata) => {
|
||||||
})
|
expect(template.styleUrls).toEqual(['package:some/module/tpl/test.css']);
|
||||||
.then((template: CompileTemplateMetadata) => {
|
async.done();
|
||||||
expect(template.styleUrls).toEqual(['package:some/module/tpl/test.css']);
|
});
|
||||||
async.done();
|
|
||||||
});
|
|
||||||
resourceLoader.flush();
|
resourceLoader.flush();
|
||||||
}));
|
}));
|
||||||
|
|
||||||
@ -238,7 +363,7 @@ export function main() {
|
|||||||
resourceLoader: SpyResourceLoader) => {
|
resourceLoader: SpyResourceLoader) => {
|
||||||
programResourceLoaderSpy(resourceLoader, {'package:some/module/test.css': 'a'});
|
programResourceLoaderSpy(resourceLoader, {'package:some/module/test.css': 'a'});
|
||||||
normalizer
|
normalizer
|
||||||
.normalizeExternalStylesheets(new CompileTemplateMetadata({
|
.normalizeExternalStylesheets(compileTemplateMetadata({
|
||||||
template: '',
|
template: '',
|
||||||
templateUrl: '',
|
templateUrl: '',
|
||||||
styleUrls: ['package:some/module/test.css']
|
styleUrls: ['package:some/module/test.css']
|
||||||
@ -264,7 +389,7 @@ export function main() {
|
|||||||
'package:some/module/test2.css': 'b'
|
'package:some/module/test2.css': 'b'
|
||||||
});
|
});
|
||||||
normalizer
|
normalizer
|
||||||
.normalizeExternalStylesheets(new CompileTemplateMetadata({
|
.normalizeExternalStylesheets(compileTemplateMetadata({
|
||||||
template: '',
|
template: '',
|
||||||
templateUrl: '',
|
templateUrl: '',
|
||||||
styleUrls: ['package:some/module/test.css']
|
styleUrls: ['package:some/module/test.css']
|
||||||
@ -301,8 +426,8 @@ export function main() {
|
|||||||
};
|
};
|
||||||
Promise
|
Promise
|
||||||
.all([
|
.all([
|
||||||
normalizer.normalizeTemplateAsync(prenormMeta),
|
normalizeTemplateAsync(normalizer, prenormMeta),
|
||||||
normalizer.normalizeTemplateAsync(prenormMeta)
|
normalizeTemplateAsync(normalizer, prenormMeta)
|
||||||
])
|
])
|
||||||
.then((templates: CompileTemplateMetadata[]) => {
|
.then((templates: CompileTemplateMetadata[]) => {
|
||||||
expect(templates[0].template).toEqual('a');
|
expect(templates[0].template).toEqual('a');
|
||||||
@ -319,8 +444,8 @@ export function main() {
|
|||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
|
|
||||||
const viewEncapsulation = ViewEncapsulation.Native;
|
const viewEncapsulation = ViewEncapsulation.Native;
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -334,8 +459,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should keep the template as html',
|
it('should keep the template as html',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -349,8 +474,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should collect ngContent',
|
it('should collect ngContent',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -364,8 +489,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should normalize ngContent wildcard selector',
|
it('should normalize ngContent wildcard selector',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -380,8 +505,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should collect top level styles in the template',
|
it('should collect top level styles in the template',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -395,8 +520,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should collect styles inside in elements',
|
it('should collect styles inside in elements',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -410,8 +535,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should collect styleUrls in the template',
|
it('should collect styleUrls in the template',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -425,8 +550,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should collect styleUrls in elements',
|
it('should collect styleUrls in elements',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -440,8 +565,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should ignore link elements with non stylesheet rel attribute',
|
it('should ignore link elements with non stylesheet rel attribute',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -455,8 +580,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should ignore link elements with absolute urls but non package: scheme',
|
it('should ignore link elements with absolute urls but non package: scheme',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -470,8 +595,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should extract @import style urls into styleAbsUrl',
|
it('should extract @import style urls into styleAbsUrl',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -486,8 +611,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should not resolve relative urls in inline styles',
|
it('should not resolve relative urls in inline styles',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -501,8 +626,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should resolve relative style urls in styleUrls',
|
it('should resolve relative style urls in styleUrls',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -517,8 +642,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should resolve relative style urls in styleUrls with http directive url',
|
it('should resolve relative style urls in styleUrls with http directive url',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_HTTP_MODULE_URL,
|
moduleUrl: SOME_HTTP_MODULE_URL,
|
||||||
@ -533,8 +658,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should normalize ViewEncapsulation.Emulated to ViewEncapsulation.None if there are no styles nor stylesheets',
|
it('should normalize ViewEncapsulation.Emulated to ViewEncapsulation.None if there are no styles nor stylesheets',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -548,8 +673,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should ignore ng-content in elements with ngNonBindable',
|
it('should ignore ng-content in elements with ngNonBindable',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
@ -564,8 +689,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should still collect <style> in elements with ngNonBindable',
|
it('should still collect <style> in elements with ngNonBindable',
|
||||||
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
inject([DirectiveNormalizer], (normalizer: DirectiveNormalizer) => {
|
||||||
const template = normalizer.normalizeLoadedTemplate(
|
const template = normalizeLoadedTemplate(
|
||||||
{
|
normalizer, {
|
||||||
ngModuleType: null,
|
ngModuleType: null,
|
||||||
componentType: SomeComp,
|
componentType: SomeComp,
|
||||||
moduleUrl: SOME_MODULE_URL,
|
moduleUrl: SOME_MODULE_URL,
|
||||||
|
@ -28,18 +28,18 @@ export function main() {
|
|||||||
|
|
||||||
function parseTemplateBindingsResult(
|
function parseTemplateBindingsResult(
|
||||||
text: string, location: any = null, prefix?: string): TemplateBindingParseResult {
|
text: string, location: any = null, prefix?: string): TemplateBindingParseResult {
|
||||||
return createParser().parseTemplateBindings(prefix, text, location);
|
return createParser().parseTemplateBindings(prefix || null, text, location);
|
||||||
}
|
}
|
||||||
function parseTemplateBindings(
|
function parseTemplateBindings(
|
||||||
text: string, location: any = null, prefix?: string): TemplateBinding[] {
|
text: string, location: any = null, prefix?: string): TemplateBinding[] {
|
||||||
return parseTemplateBindingsResult(text, location, prefix).templateBindings;
|
return parseTemplateBindingsResult(text, location, prefix).templateBindings;
|
||||||
}
|
}
|
||||||
|
|
||||||
function parseInterpolation(text: string, location: any = null): ASTWithSource {
|
function parseInterpolation(text: string, location: any = null): ASTWithSource|null {
|
||||||
return createParser().parseInterpolation(text, location);
|
return createParser().parseInterpolation(text, location);
|
||||||
}
|
}
|
||||||
|
|
||||||
function splitInterpolation(text: string, location: any = null): SplitInterpolation {
|
function splitInterpolation(text: string, location: any = null): SplitInterpolation|null {
|
||||||
return createParser().splitInterpolation(text, location);
|
return createParser().splitInterpolation(text, location);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -48,7 +48,7 @@ export function main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function checkInterpolation(exp: string, expected?: string) {
|
function checkInterpolation(exp: string, expected?: string) {
|
||||||
const ast = parseInterpolation(exp);
|
const ast = parseInterpolation(exp) !;
|
||||||
if (expected == null) expected = exp;
|
if (expected == null) expected = exp;
|
||||||
expect(unparse(ast)).toEqual(expected);
|
expect(unparse(ast)).toEqual(expected);
|
||||||
validate(ast);
|
validate(ast);
|
||||||
@ -475,7 +475,7 @@ export function main() {
|
|||||||
() => { expect(parseInterpolation('nothing')).toBe(null); });
|
() => { expect(parseInterpolation('nothing')).toBe(null); });
|
||||||
|
|
||||||
it('should parse no prefix/suffix interpolation', () => {
|
it('should parse no prefix/suffix interpolation', () => {
|
||||||
const ast = parseInterpolation('{{a}}').ast as Interpolation;
|
const ast = parseInterpolation('{{a}}') !.ast as Interpolation;
|
||||||
expect(ast.strings).toEqual(['', '']);
|
expect(ast.strings).toEqual(['', '']);
|
||||||
expect(ast.expressions.length).toEqual(1);
|
expect(ast.expressions.length).toEqual(1);
|
||||||
expect(ast.expressions[0].name).toEqual('a');
|
expect(ast.expressions[0].name).toEqual('a');
|
||||||
@ -483,18 +483,18 @@ export function main() {
|
|||||||
|
|
||||||
it('should parse prefix/suffix with multiple interpolation', () => {
|
it('should parse prefix/suffix with multiple interpolation', () => {
|
||||||
const originalExp = 'before {{ a }} middle {{ b }} after';
|
const originalExp = 'before {{ a }} middle {{ b }} after';
|
||||||
const ast = parseInterpolation(originalExp).ast;
|
const ast = parseInterpolation(originalExp) !.ast;
|
||||||
expect(unparse(ast)).toEqual(originalExp);
|
expect(unparse(ast)).toEqual(originalExp);
|
||||||
validate(ast);
|
validate(ast);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should report empty interpolation expressions', () => {
|
it('should report empty interpolation expressions', () => {
|
||||||
expectError(
|
expectError(
|
||||||
parseInterpolation('{{}}'),
|
parseInterpolation('{{}}') !,
|
||||||
'Blank expressions are not allowed in interpolated strings');
|
'Blank expressions are not allowed in interpolated strings');
|
||||||
|
|
||||||
expectError(
|
expectError(
|
||||||
parseInterpolation('foo {{ }}'),
|
parseInterpolation('foo {{ }}') !,
|
||||||
'Parser Error: Blank expressions are not allowed in interpolated strings');
|
'Parser Error: Blank expressions are not allowed in interpolated strings');
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -507,7 +507,8 @@ export function main() {
|
|||||||
|
|
||||||
it('should support custom interpolation', () => {
|
it('should support custom interpolation', () => {
|
||||||
const parser = new Parser(new Lexer());
|
const parser = new Parser(new Lexer());
|
||||||
const ast = parser.parseInterpolation('{% a %}', null, {start: '{%', end: '%}'}).ast as any;
|
const ast =
|
||||||
|
parser.parseInterpolation('{% a %}', null, {start: '{%', end: '%}'}) !.ast as any;
|
||||||
expect(ast.strings).toEqual(['', '']);
|
expect(ast.strings).toEqual(['', '']);
|
||||||
expect(ast.expressions.length).toEqual(1);
|
expect(ast.expressions.length).toEqual(1);
|
||||||
expect(ast.expressions[0].name).toEqual('a');
|
expect(ast.expressions[0].name).toEqual('a');
|
||||||
@ -586,12 +587,12 @@ export function main() {
|
|||||||
|
|
||||||
describe('offsets', () => {
|
describe('offsets', () => {
|
||||||
it('should retain the offsets of an interpolation', () => {
|
it('should retain the offsets of an interpolation', () => {
|
||||||
const interpolations = splitInterpolation('{{a}} {{b}} {{c}}');
|
const interpolations = splitInterpolation('{{a}} {{b}} {{c}}') !;
|
||||||
expect(interpolations.offsets).toEqual([2, 9, 16]);
|
expect(interpolations.offsets).toEqual([2, 9, 16]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should retain the offsets into the expression AST of interpolations', () => {
|
it('should retain the offsets into the expression AST of interpolations', () => {
|
||||||
const source = parseInterpolation('{{a}} {{b}} {{c}}');
|
const source = parseInterpolation('{{a}} {{b}} {{c}}') !;
|
||||||
const interpolation = source.ast as Interpolation;
|
const interpolation = source.ast as Interpolation;
|
||||||
expect(interpolation.expressions.map(e => e.span.start)).toEqual([2, 9, 16]);
|
expect(interpolation.expressions.map(e => e.span.start)).toEqual([2, 9, 16]);
|
||||||
});
|
});
|
||||||
|
@ -67,7 +67,7 @@ class Unparser implements AstVisitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
visitFunctionCall(ast: FunctionCall, context: any) {
|
visitFunctionCall(ast: FunctionCall, context: any) {
|
||||||
this._visit(ast.target);
|
this._visit(ast.target !);
|
||||||
this._expression += '(';
|
this._expression += '(';
|
||||||
let isFirst = true;
|
let isFirst = true;
|
||||||
ast.args.forEach(arg => {
|
ast.args.forEach(arg => {
|
||||||
|
@ -285,7 +285,7 @@ export function main() {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it('should allow nested implicit elements', () => {
|
it('should allow nested implicit elements', () => {
|
||||||
let result: any[];
|
let result: any[] = undefined !;
|
||||||
|
|
||||||
expect(() => {
|
expect(() => {
|
||||||
result = extract('<div>outer<div>inner</div></div>', ['div']);
|
result = extract('<div>outer<div>inner</div></div>', ['div']);
|
||||||
@ -490,7 +490,7 @@ function fakeTranslate(
|
|||||||
messages.forEach(message => {
|
messages.forEach(message => {
|
||||||
const id = digest(message);
|
const id = digest(message);
|
||||||
const text = serializeI18nNodes(message.nodes).join('').replace(/</g, '[');
|
const text = serializeI18nNodes(message.nodes).join('').replace(/</g, '[');
|
||||||
i18nMsgMap[id] = [new i18n.Text(`**${text}**`, null)];
|
i18nMsgMap[id] = [new i18n.Text(`**${text}**`, null !)];
|
||||||
});
|
});
|
||||||
|
|
||||||
const translations = new TranslationBundle(i18nMsgMap, null, digest);
|
const translations = new TranslationBundle(i18nMsgMap, null, digest);
|
||||||
|
@ -36,13 +36,13 @@ export function main(): void {
|
|||||||
const visitor = new RecurseVisitor();
|
const visitor = new RecurseVisitor();
|
||||||
const container = new i18n.Container(
|
const container = new i18n.Container(
|
||||||
[
|
[
|
||||||
new i18n.Text('', null),
|
new i18n.Text('', null !),
|
||||||
new i18n.Placeholder('', '', null),
|
new i18n.Placeholder('', '', null !),
|
||||||
new i18n.IcuPlaceholder(null, '', null),
|
new i18n.IcuPlaceholder(null !, '', null !),
|
||||||
],
|
],
|
||||||
null);
|
null !);
|
||||||
const tag = new i18n.TagPlaceholder('', {}, '', '', [container], false, null);
|
const tag = new i18n.TagPlaceholder('', {}, '', '', [container], false, null !);
|
||||||
const icu = new i18n.Icu('', '', {tag}, null);
|
const icu = new i18n.Icu('', '', {tag}, null !);
|
||||||
|
|
||||||
icu.visit(visitor);
|
icu.visit(visitor);
|
||||||
expect(visitor.textCount).toEqual(1);
|
expect(visitor.textCount).toEqual(1);
|
||||||
|
@ -117,7 +117,7 @@ export function main(): void {
|
|||||||
</translationbundle>`;
|
</translationbundle>`;
|
||||||
|
|
||||||
// Invalid messages should not cause the parser to throw
|
// Invalid messages should not cause the parser to throw
|
||||||
let i18nNodesByMsgId: {[id: string]: i18n.Node[]};
|
let i18nNodesByMsgId: {[id: string]: i18n.Node[]} = undefined !;
|
||||||
expect(() => {
|
expect(() => {
|
||||||
i18nNodesByMsgId = serializer.load(XTB, 'url').i18nNodesByMsgId;
|
i18nNodesByMsgId = serializer.load(XTB, 'url').i18nNodesByMsgId;
|
||||||
}).not.toThrow();
|
}).not.toThrow();
|
||||||
|
@ -18,11 +18,11 @@ export function main(): void {
|
|||||||
describe('TranslationBundle', () => {
|
describe('TranslationBundle', () => {
|
||||||
const file = new ParseSourceFile('content', 'url');
|
const file = new ParseSourceFile('content', 'url');
|
||||||
const location = new ParseLocation(file, 0, 0, 0);
|
const location = new ParseLocation(file, 0, 0, 0);
|
||||||
const span = new ParseSourceSpan(location, null);
|
const span = new ParseSourceSpan(location, null !);
|
||||||
const srcNode = new i18n.Text('src', span);
|
const srcNode = new i18n.Text('src', span);
|
||||||
|
|
||||||
it('should translate a plain message', () => {
|
it('should translate a plain message', () => {
|
||||||
const msgMap = {foo: [new i18n.Text('bar', null)]};
|
const msgMap = {foo: [new i18n.Text('bar', null !)]};
|
||||||
const tb = new TranslationBundle(msgMap, null, (_) => 'foo');
|
const tb = new TranslationBundle(msgMap, null, (_) => 'foo');
|
||||||
const msg = new i18n.Message([srcNode], {}, {}, 'm', 'd', 'i');
|
const msg = new i18n.Message([srcNode], {}, {}, 'm', 'd', 'i');
|
||||||
expect(serializeNodes(tb.get(msg))).toEqual(['bar']);
|
expect(serializeNodes(tb.get(msg))).toEqual(['bar']);
|
||||||
@ -31,8 +31,8 @@ export function main(): void {
|
|||||||
it('should translate a message with placeholder', () => {
|
it('should translate a message with placeholder', () => {
|
||||||
const msgMap = {
|
const msgMap = {
|
||||||
foo: [
|
foo: [
|
||||||
new i18n.Text('bar', null),
|
new i18n.Text('bar', null !),
|
||||||
new i18n.Placeholder('', 'ph1', null),
|
new i18n.Placeholder('', 'ph1', null !),
|
||||||
]
|
]
|
||||||
};
|
};
|
||||||
const phMap = {
|
const phMap = {
|
||||||
@ -46,12 +46,12 @@ export function main(): void {
|
|||||||
it('should translate a message with placeholder referencing messages', () => {
|
it('should translate a message with placeholder referencing messages', () => {
|
||||||
const msgMap = {
|
const msgMap = {
|
||||||
foo: [
|
foo: [
|
||||||
new i18n.Text('--', null),
|
new i18n.Text('--', null !),
|
||||||
new i18n.Placeholder('', 'ph1', null),
|
new i18n.Placeholder('', 'ph1', null !),
|
||||||
new i18n.Text('++', null),
|
new i18n.Text('++', null !),
|
||||||
],
|
],
|
||||||
ref: [
|
ref: [
|
||||||
new i18n.Text('*refMsg*', null),
|
new i18n.Text('*refMsg*', null !),
|
||||||
],
|
],
|
||||||
};
|
};
|
||||||
const refMsg = new i18n.Message([srcNode], {}, {}, 'm', 'd', 'i');
|
const refMsg = new i18n.Message([srcNode], {}, {}, 'm', 'd', 'i');
|
||||||
@ -70,13 +70,13 @@ export function main(): void {
|
|||||||
|
|
||||||
const digest = (_: any) => `no matching id`;
|
const digest = (_: any) => `no matching id`;
|
||||||
// Empty message map -> use source messages in Ignore mode
|
// Empty message map -> use source messages in Ignore mode
|
||||||
let tb = new TranslationBundle({}, null, digest, null, MissingTranslationStrategy.Ignore);
|
let tb = new TranslationBundle({}, null, digest, null !, MissingTranslationStrategy.Ignore);
|
||||||
expect(serializeNodes(tb.get(messages[0])).join('')).toEqual(src);
|
expect(serializeNodes(tb.get(messages[0])).join('')).toEqual(src);
|
||||||
// Empty message map -> use source messages in Warning mode
|
// Empty message map -> use source messages in Warning mode
|
||||||
tb = new TranslationBundle({}, null, digest, null, MissingTranslationStrategy.Warning);
|
tb = new TranslationBundle({}, null, digest, null !, MissingTranslationStrategy.Warning);
|
||||||
expect(serializeNodes(tb.get(messages[0])).join('')).toEqual(src);
|
expect(serializeNodes(tb.get(messages[0])).join('')).toEqual(src);
|
||||||
// Empty message map -> throw in Error mode
|
// Empty message map -> throw in Error mode
|
||||||
tb = new TranslationBundle({}, null, digest, null, MissingTranslationStrategy.Error);
|
tb = new TranslationBundle({}, null, digest, null !, MissingTranslationStrategy.Error);
|
||||||
expect(() => serializeNodes(tb.get(messages[0])).join('')).toThrow();
|
expect(() => serializeNodes(tb.get(messages[0])).join('')).toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -84,7 +84,7 @@ export function main(): void {
|
|||||||
it('should report unknown placeholders', () => {
|
it('should report unknown placeholders', () => {
|
||||||
const msgMap = {
|
const msgMap = {
|
||||||
foo: [
|
foo: [
|
||||||
new i18n.Text('bar', null),
|
new i18n.Text('bar', null !),
|
||||||
new i18n.Placeholder('', 'ph1', span),
|
new i18n.Placeholder('', 'ph1', span),
|
||||||
]
|
]
|
||||||
};
|
};
|
||||||
@ -95,7 +95,7 @@ export function main(): void {
|
|||||||
|
|
||||||
it('should report missing translation', () => {
|
it('should report missing translation', () => {
|
||||||
const tb =
|
const tb =
|
||||||
new TranslationBundle({}, null, (_) => 'foo', null, MissingTranslationStrategy.Error);
|
new TranslationBundle({}, null, (_) => 'foo', null !, MissingTranslationStrategy.Error);
|
||||||
const msg = new i18n.Message([srcNode], {}, {}, 'm', 'd', 'i');
|
const msg = new i18n.Message([srcNode], {}, {}, 'm', 'd', 'i');
|
||||||
expect(() => tb.get(msg)).toThrowError(/Missing translation for message "foo"/);
|
expect(() => tb.get(msg)).toThrowError(/Missing translation for message "foo"/);
|
||||||
});
|
});
|
||||||
@ -108,7 +108,7 @@ export function main(): void {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const tb = new TranslationBundle(
|
const tb = new TranslationBundle(
|
||||||
{}, 'en', (_) => 'foo', null, MissingTranslationStrategy.Warning, console);
|
{}, 'en', (_) => 'foo', null !, MissingTranslationStrategy.Warning, console);
|
||||||
const msg = new i18n.Message([srcNode], {}, {}, 'm', 'd', 'i');
|
const msg = new i18n.Message([srcNode], {}, {}, 'm', 'd', 'i');
|
||||||
|
|
||||||
expect(() => tb.get(msg)).not.toThrowError();
|
expect(() => tb.get(msg)).not.toThrowError();
|
||||||
@ -117,8 +117,8 @@ export function main(): void {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it('should not report missing translation with MissingTranslationStrategy.Ignore', () => {
|
it('should not report missing translation with MissingTranslationStrategy.Ignore', () => {
|
||||||
const tb =
|
const tb = new TranslationBundle(
|
||||||
new TranslationBundle({}, null, (_) => 'foo', null, MissingTranslationStrategy.Ignore);
|
{}, null, (_) => 'foo', null !, MissingTranslationStrategy.Ignore);
|
||||||
const msg = new i18n.Message([srcNode], {}, {}, 'm', 'd', 'i');
|
const msg = new i18n.Message([srcNode], {}, {}, 'm', 'd', 'i');
|
||||||
expect(() => tb.get(msg)).not.toThrowError();
|
expect(() => tb.get(msg)).not.toThrowError();
|
||||||
});
|
});
|
||||||
@ -132,15 +132,15 @@ export function main(): void {
|
|||||||
let count = 0;
|
let count = 0;
|
||||||
const digest = (_: any) => count++ ? 'ref' : 'foo';
|
const digest = (_: any) => count++ ? 'ref' : 'foo';
|
||||||
const tb =
|
const tb =
|
||||||
new TranslationBundle(msgMap, null, digest, null, MissingTranslationStrategy.Error);
|
new TranslationBundle(msgMap, null, digest, null !, MissingTranslationStrategy.Error);
|
||||||
expect(() => tb.get(msg)).toThrowError(/Missing translation for message "ref"/);
|
expect(() => tb.get(msg)).toThrowError(/Missing translation for message "ref"/);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should report invalid translated html', () => {
|
it('should report invalid translated html', () => {
|
||||||
const msgMap = {
|
const msgMap = {
|
||||||
foo: [
|
foo: [
|
||||||
new i18n.Text('text', null),
|
new i18n.Text('text', null !),
|
||||||
new i18n.Placeholder('', 'ph1', null),
|
new i18n.Placeholder('', 'ph1', null !),
|
||||||
]
|
]
|
||||||
};
|
};
|
||||||
const phMap = {
|
const phMap = {
|
||||||
|
@ -16,7 +16,7 @@ export function main() {
|
|||||||
let fixture: ComponentFixture<TestComponent>;
|
let fixture: ComponentFixture<TestComponent>;
|
||||||
|
|
||||||
|
|
||||||
describe('directives', () => {
|
describe('directiv es', () => {
|
||||||
it('should support dotted selectors', async(() => {
|
it('should support dotted selectors', async(() => {
|
||||||
@Directive({selector: '[dot.name]'})
|
@Directive({selector: '[dot.name]'})
|
||||||
class MyDir {
|
class MyDir {
|
||||||
|
@ -26,9 +26,9 @@ class SomeMetadata implements SomeMetadataType {
|
|||||||
arrayProp: any[];
|
arrayProp: any[];
|
||||||
|
|
||||||
constructor(options: SomeMetadataType) {
|
constructor(options: SomeMetadataType) {
|
||||||
this.plainProp = options.plainProp;
|
this.plainProp = options.plainProp !;
|
||||||
this._getterProp = options.getterProp;
|
this._getterProp = options.getterProp !;
|
||||||
this.arrayProp = options.arrayProp;
|
this.arrayProp = options.arrayProp !;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -42,7 +42,7 @@ class OtherMetadata extends SomeMetadata implements OtherMetadataType {
|
|||||||
arrayProp: options.arrayProp
|
arrayProp: options.arrayProp
|
||||||
});
|
});
|
||||||
|
|
||||||
this.otherPlainProp = options.otherPlainProp;
|
this.otherPlainProp = options.otherPlainProp !;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -215,7 +215,7 @@ export function main() {
|
|||||||
|
|
||||||
it('should throw with descriptive error message when null is passed to declarations',
|
it('should throw with descriptive error message when null is passed to declarations',
|
||||||
inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => {
|
inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => {
|
||||||
@NgModule({declarations: [null]})
|
@NgModule({declarations: [null !]})
|
||||||
class ModuleWithNullDeclared {
|
class ModuleWithNullDeclared {
|
||||||
}
|
}
|
||||||
expect(() => resolver.loadNgModuleDirectiveAndPipeMetadata(ModuleWithNullDeclared, true))
|
expect(() => resolver.loadNgModuleDirectiveAndPipeMetadata(ModuleWithNullDeclared, true))
|
||||||
@ -225,7 +225,7 @@ export function main() {
|
|||||||
|
|
||||||
it('should throw with descriptive error message when null is passed to imports',
|
it('should throw with descriptive error message when null is passed to imports',
|
||||||
inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => {
|
inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => {
|
||||||
@NgModule({imports: [null]})
|
@NgModule({imports: [null !]})
|
||||||
class ModuleWithNullImported {
|
class ModuleWithNullImported {
|
||||||
}
|
}
|
||||||
expect(() => resolver.loadNgModuleDirectiveAndPipeMetadata(ModuleWithNullImported, true))
|
expect(() => resolver.loadNgModuleDirectiveAndPipeMetadata(ModuleWithNullImported, true))
|
||||||
@ -246,7 +246,7 @@ export function main() {
|
|||||||
|
|
||||||
it('should throw with descriptive error message when encounter invalid provider',
|
it('should throw with descriptive error message when encounter invalid provider',
|
||||||
inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => {
|
inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => {
|
||||||
@NgModule({providers: [{provide: SimpleService, useClass: undefined}]})
|
@NgModule({providers: [{provide: SimpleService, useClass: undefined !}]})
|
||||||
class SomeModule {
|
class SomeModule {
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -256,7 +256,7 @@ export function main() {
|
|||||||
|
|
||||||
it('should throw with descriptive error message when provider is undefined',
|
it('should throw with descriptive error message when provider is undefined',
|
||||||
inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => {
|
inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => {
|
||||||
@NgModule({providers: [undefined]})
|
@NgModule({providers: [undefined !]})
|
||||||
class SomeModule {
|
class SomeModule {
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -288,10 +288,10 @@ export function main() {
|
|||||||
|
|
||||||
it('should throw with descriptive error message when null or undefined is passed to module bootstrap',
|
it('should throw with descriptive error message when null or undefined is passed to module bootstrap',
|
||||||
inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => {
|
inject([CompileMetadataResolver], (resolver: CompileMetadataResolver) => {
|
||||||
@NgModule({bootstrap: [null]})
|
@NgModule({bootstrap: [null !]})
|
||||||
class ModuleWithNullBootstrap {
|
class ModuleWithNullBootstrap {
|
||||||
}
|
}
|
||||||
@NgModule({bootstrap: [undefined]})
|
@NgModule({bootstrap: [undefined !]})
|
||||||
class ModuleWithUndefinedBootstrap {
|
class ModuleWithUndefinedBootstrap {
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -410,7 +410,7 @@ export function main() {
|
|||||||
class MyModule {
|
class MyModule {
|
||||||
}
|
}
|
||||||
|
|
||||||
const modMeta = resolver.getNgModuleMetadata(MyModule);
|
const modMeta = resolver.getNgModuleMetadata(MyModule) !;
|
||||||
expect(modMeta.declaredDirectives.length).toBe(1);
|
expect(modMeta.declaredDirectives.length).toBe(1);
|
||||||
expect(modMeta.declaredDirectives[0].reference).toBe(MyComp);
|
expect(modMeta.declaredDirectives[0].reference).toBe(MyComp);
|
||||||
}));
|
}));
|
||||||
@ -480,11 +480,12 @@ class MyBrokenComp2 {
|
|||||||
class SimpleService {
|
class SimpleService {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Component({selector: 'my-broken-comp', template: '', providers: [SimpleService, null, [null]]})
|
@Component({selector: 'my-broken-comp', template: '', providers: [SimpleService, null !, [null]]})
|
||||||
class MyBrokenComp3 {
|
class MyBrokenComp3 {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Component({selector: 'my-broken-comp', template: '', viewProviders: [null, SimpleService, [null]]})
|
@Component(
|
||||||
|
{selector: 'my-broken-comp', template: '', viewProviders: [null !, SimpleService, [null]]})
|
||||||
class MyBrokenComp4 {
|
class MyBrokenComp4 {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -78,7 +78,7 @@ class _Humanizer implements html.Visitor {
|
|||||||
|
|
||||||
private _appendContext(ast: html.Node, input: any[]): any[] {
|
private _appendContext(ast: html.Node, input: any[]): any[] {
|
||||||
if (!this.includeSourceSpan) return input;
|
if (!this.includeSourceSpan) return input;
|
||||||
input.push(ast.sourceSpan.toString());
|
input.push(ast.sourceSpan !.toString());
|
||||||
return input;
|
return input;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -395,11 +395,11 @@ export function main() {
|
|||||||
it('should set the start and end source spans', () => {
|
it('should set the start and end source spans', () => {
|
||||||
const node = <html.Element>parser.parse('<div>a</div>', 'TestComp').rootNodes[0];
|
const node = <html.Element>parser.parse('<div>a</div>', 'TestComp').rootNodes[0];
|
||||||
|
|
||||||
expect(node.startSourceSpan.start.offset).toEqual(0);
|
expect(node.startSourceSpan !.start.offset).toEqual(0);
|
||||||
expect(node.startSourceSpan.end.offset).toEqual(5);
|
expect(node.startSourceSpan !.end.offset).toEqual(5);
|
||||||
|
|
||||||
expect(node.endSourceSpan.start.offset).toEqual(6);
|
expect(node.endSourceSpan !.start.offset).toEqual(6);
|
||||||
expect(node.endSourceSpan.end.offset).toEqual(12);
|
expect(node.endSourceSpan !.end.offset).toEqual(12);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should support expansion form', () => {
|
it('should support expansion form', () => {
|
||||||
@ -420,8 +420,8 @@ export function main() {
|
|||||||
it('should report a value span for an attibute with a value', () => {
|
it('should report a value span for an attibute with a value', () => {
|
||||||
const ast = parser.parse('<div bar="12"></div>', 'TestComp');
|
const ast = parser.parse('<div bar="12"></div>', 'TestComp');
|
||||||
const attr = (ast.rootNodes[0] as html.Element).attrs[0];
|
const attr = (ast.rootNodes[0] as html.Element).attrs[0];
|
||||||
expect(attr.valueSpan.start.offset).toEqual(9);
|
expect(attr.valueSpan !.start.offset).toEqual(9);
|
||||||
expect(attr.valueSpan.end.offset).toEqual(13);
|
expect(attr.valueSpan !.end.offset).toEqual(13);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -56,28 +56,28 @@ export function main() {
|
|||||||
const nodes = expand(`{messages.length, plural,=0 {<b>bold</b>}}`).nodes;
|
const nodes = expand(`{messages.length, plural,=0 {<b>bold</b>}}`).nodes;
|
||||||
|
|
||||||
const container: html.Element = <html.Element>nodes[0];
|
const container: html.Element = <html.Element>nodes[0];
|
||||||
expect(container.sourceSpan.start.col).toEqual(0);
|
expect(container.sourceSpan !.start.col).toEqual(0);
|
||||||
expect(container.sourceSpan.end.col).toEqual(42);
|
expect(container.sourceSpan !.end.col).toEqual(42);
|
||||||
expect(container.startSourceSpan.start.col).toEqual(0);
|
expect(container.startSourceSpan !.start.col).toEqual(0);
|
||||||
expect(container.startSourceSpan.end.col).toEqual(42);
|
expect(container.startSourceSpan !.end.col).toEqual(42);
|
||||||
expect(container.endSourceSpan.start.col).toEqual(0);
|
expect(container.endSourceSpan !.start.col).toEqual(0);
|
||||||
expect(container.endSourceSpan.end.col).toEqual(42);
|
expect(container.endSourceSpan !.end.col).toEqual(42);
|
||||||
|
|
||||||
const switchExp = container.attrs[0];
|
const switchExp = container.attrs[0];
|
||||||
expect(switchExp.sourceSpan.start.col).toEqual(1);
|
expect(switchExp.sourceSpan.start.col).toEqual(1);
|
||||||
expect(switchExp.sourceSpan.end.col).toEqual(16);
|
expect(switchExp.sourceSpan.end.col).toEqual(16);
|
||||||
|
|
||||||
const template: html.Element = <html.Element>container.children[0];
|
const template: html.Element = <html.Element>container.children[0];
|
||||||
expect(template.sourceSpan.start.col).toEqual(25);
|
expect(template.sourceSpan !.start.col).toEqual(25);
|
||||||
expect(template.sourceSpan.end.col).toEqual(41);
|
expect(template.sourceSpan !.end.col).toEqual(41);
|
||||||
|
|
||||||
const switchCheck = template.attrs[0];
|
const switchCheck = template.attrs[0];
|
||||||
expect(switchCheck.sourceSpan.start.col).toEqual(25);
|
expect(switchCheck.sourceSpan.start.col).toEqual(25);
|
||||||
expect(switchCheck.sourceSpan.end.col).toEqual(28);
|
expect(switchCheck.sourceSpan.end.col).toEqual(28);
|
||||||
|
|
||||||
const b: html.Element = <html.Element>template.children[0];
|
const b: html.Element = <html.Element>template.children[0];
|
||||||
expect(b.sourceSpan.start.col).toEqual(29);
|
expect(b.sourceSpan !.start.col).toEqual(29);
|
||||||
expect(b.endSourceSpan.end.col).toEqual(40);
|
expect(b.endSourceSpan !.end.col).toEqual(40);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should handle other special forms', () => {
|
it('should handle other special forms', () => {
|
||||||
|
@ -443,7 +443,7 @@ export function main() {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it('should parse interpolation with custom markers', () => {
|
it('should parse interpolation with custom markers', () => {
|
||||||
expect(tokenizeAndHumanizeParts('{% a %}', null, {start: '{%', end: '%}'})).toEqual([
|
expect(tokenizeAndHumanizeParts('{% a %}', null !, {start: '{%', end: '%}'})).toEqual([
|
||||||
[lex.TokenType.TEXT, '{% a %}'],
|
[lex.TokenType.TEXT, '{% a %}'],
|
||||||
[lex.TokenType.EOF],
|
[lex.TokenType.EOF],
|
||||||
]);
|
]);
|
||||||
@ -769,7 +769,7 @@ export function main() {
|
|||||||
const file = new ParseSourceFile(src, 'file://');
|
const file = new ParseSourceFile(src, 'file://');
|
||||||
const location = new ParseLocation(file, 12, 123, 456);
|
const location = new ParseLocation(file, 12, 123, 456);
|
||||||
const span = new ParseSourceSpan(location, location);
|
const span = new ParseSourceSpan(location, location);
|
||||||
const error = new lex.TokenError('**ERROR**', null, span);
|
const error = new lex.TokenError('**ERROR**', null !, span);
|
||||||
expect(error.toString())
|
expect(error.toString())
|
||||||
.toEqual(`**ERROR** ("\n222\n333\n[ERROR ->]E\n444\n555\n"): file://@123:456`);
|
.toEqual(`**ERROR** ("\n222\n333\n[ERROR ->]E\n444\n555\n"): file://@123:456`);
|
||||||
});
|
});
|
||||||
|
@ -25,7 +25,7 @@ export function main() {
|
|||||||
ctx.print(createSourceSpan(fileA, 1), 'o1');
|
ctx.print(createSourceSpan(fileA, 1), 'o1');
|
||||||
ctx.print(createSourceSpan(fileB, 0), 'o2');
|
ctx.print(createSourceSpan(fileB, 0), 'o2');
|
||||||
ctx.print(createSourceSpan(fileB, 1), 'o3');
|
ctx.print(createSourceSpan(fileB, 1), 'o3');
|
||||||
const sm = ctx.toSourceMapGenerator('o.ts', 'o.js').toJSON();
|
const sm = ctx.toSourceMapGenerator('o.ts', 'o.js').toJSON() !;
|
||||||
expect(sm.sources).toEqual([fileA.url, fileB.url]);
|
expect(sm.sources).toEqual([fileA.url, fileB.url]);
|
||||||
expect(sm.sourcesContent).toEqual([fileA.content, fileB.content]);
|
expect(sm.sourcesContent).toEqual([fileA.content, fileB.content]);
|
||||||
});
|
});
|
||||||
@ -43,7 +43,7 @@ export function main() {
|
|||||||
it('should be able to shift the content', () => {
|
it('should be able to shift the content', () => {
|
||||||
ctx.print(createSourceSpan(fileA, 0), 'fileA-0');
|
ctx.print(createSourceSpan(fileA, 0), 'fileA-0');
|
||||||
|
|
||||||
const sm = ctx.toSourceMapGenerator('o.ts', 'o.js', 10).toJSON();
|
const sm = ctx.toSourceMapGenerator('o.ts', 'o.js', 10).toJSON() !;
|
||||||
expect(originalPositionFor(sm, {line: 11, column: 0})).toEqual({
|
expect(originalPositionFor(sm, {line: 11, column: 0})).toEqual({
|
||||||
line: 1,
|
line: 1,
|
||||||
column: 0,
|
column: 0,
|
||||||
@ -111,9 +111,9 @@ export function main() {
|
|||||||
// All lines / columns indexes are 0-based
|
// All lines / columns indexes are 0-based
|
||||||
// Note: source-map line indexes are 1-based, column 0-based
|
// Note: source-map line indexes are 1-based, column 0-based
|
||||||
function expectMap(
|
function expectMap(
|
||||||
ctx: EmitterVisitorContext, genLine: number, genCol: number, source: string = null,
|
ctx: EmitterVisitorContext, genLine: number, genCol: number, source: string | null = null,
|
||||||
srcLine: number = null, srcCol: number = null) {
|
srcLine: number | null = null, srcCol: number | null = null) {
|
||||||
const sm = ctx.toSourceMapGenerator('o.ts', 'o.js').toJSON();
|
const sm = ctx.toSourceMapGenerator('o.ts', 'o.js').toJSON() !;
|
||||||
const genPosition = {line: genLine + 1, column: genCol};
|
const genPosition = {line: genLine + 1, column: genCol};
|
||||||
const origPosition = originalPositionFor(sm, genPosition);
|
const origPosition = originalPositionFor(sm, genPosition);
|
||||||
expect(origPosition.source).toEqual(source);
|
expect(origPosition.source).toEqual(source);
|
||||||
@ -123,7 +123,7 @@ function expectMap(
|
|||||||
|
|
||||||
// returns the number of segments per line
|
// returns the number of segments per line
|
||||||
function nbSegmentsPerLine(ctx: EmitterVisitorContext) {
|
function nbSegmentsPerLine(ctx: EmitterVisitorContext) {
|
||||||
const sm = ctx.toSourceMapGenerator('o.ts', 'o.js').toJSON();
|
const sm = ctx.toSourceMapGenerator('o.ts', 'o.js').toJSON() !;
|
||||||
const lines = sm.mappings.split(';');
|
const lines = sm.mappings.split(';');
|
||||||
return lines.map(l => {
|
return lines.map(l => {
|
||||||
const m = l.match(/,/g);
|
const m = l.match(/,/g);
|
||||||
|
@ -23,8 +23,8 @@ class SimpleJsImportGenerator implements ImportResolver {
|
|||||||
fileNameToModuleName(importedUrlStr: string, moduleUrlStr: string): string {
|
fileNameToModuleName(importedUrlStr: string, moduleUrlStr: string): string {
|
||||||
return importedUrlStr;
|
return importedUrlStr;
|
||||||
}
|
}
|
||||||
getImportAs(symbol: StaticSymbol): StaticSymbol { return null; }
|
getImportAs(symbol: StaticSymbol): StaticSymbol|null { return null; }
|
||||||
getTypeArity(symbol: StaticSymbol): number /*|null*/ { return null; }
|
getTypeArity(symbol: StaticSymbol): number|null { return null; }
|
||||||
}
|
}
|
||||||
|
|
||||||
export function main() {
|
export function main() {
|
||||||
@ -39,12 +39,12 @@ export function main() {
|
|||||||
});
|
});
|
||||||
|
|
||||||
function emitSourceMap(
|
function emitSourceMap(
|
||||||
stmt: o.Statement | o.Statement[], exportedVars: string[] = null,
|
stmt: o.Statement | o.Statement[], exportedVars: string[] | null = null,
|
||||||
preamble?: string): SourceMap {
|
preamble?: string): SourceMap {
|
||||||
const stmts = Array.isArray(stmt) ? stmt : [stmt];
|
const stmts = Array.isArray(stmt) ? stmt : [stmt];
|
||||||
const source = emitter.emitStatements(
|
const source = emitter.emitStatements(
|
||||||
someSourceFilePath, someGenFilePath, stmts, exportedVars || [], preamble);
|
someSourceFilePath, someGenFilePath, stmts, exportedVars || [], preamble);
|
||||||
return extractSourceMap(source);
|
return extractSourceMap(source) !;
|
||||||
}
|
}
|
||||||
|
|
||||||
describe('source maps', () => {
|
describe('source maps', () => {
|
||||||
|
@ -29,8 +29,8 @@ class SimpleJsImportGenerator implements ImportResolver {
|
|||||||
fileNameToModuleName(importedUrlStr: string, moduleUrlStr: string): string {
|
fileNameToModuleName(importedUrlStr: string, moduleUrlStr: string): string {
|
||||||
return importedUrlStr;
|
return importedUrlStr;
|
||||||
}
|
}
|
||||||
getImportAs(symbol: StaticSymbol): StaticSymbol { return null; }
|
getImportAs(symbol: StaticSymbol): StaticSymbol|null { return null; }
|
||||||
getTypeArity(symbol: StaticSymbol): number /*|null*/ { return null; }
|
getTypeArity(symbol: StaticSymbol): number|null { return null; }
|
||||||
}
|
}
|
||||||
|
|
||||||
export function main() {
|
export function main() {
|
||||||
@ -49,7 +49,8 @@ export function main() {
|
|||||||
someVar = o.variable('someVar');
|
someVar = o.variable('someVar');
|
||||||
});
|
});
|
||||||
|
|
||||||
function emitStmt(stmt: o.Statement, exportedVars: string[] = null, preamble?: string): string {
|
function emitStmt(
|
||||||
|
stmt: o.Statement, exportedVars: string[] | null = null, preamble?: string): string {
|
||||||
const source = emitter.emitStatements(
|
const source = emitter.emitStatements(
|
||||||
someSourceFilePath, someGenFilePath, [stmt], exportedVars || [], preamble);
|
someSourceFilePath, someGenFilePath, [stmt], exportedVars || [], preamble);
|
||||||
return stripSourceMapAndNewLine(source);
|
return stripSourceMapAndNewLine(source);
|
||||||
@ -224,15 +225,15 @@ export function main() {
|
|||||||
beforeEach(() => { callSomeMethod = o.THIS_EXPR.callMethod('someMethod', []).toStmt(); });
|
beforeEach(() => { callSomeMethod = o.THIS_EXPR.callMethod('someMethod', []).toStmt(); });
|
||||||
|
|
||||||
it('should support declaring classes', () => {
|
it('should support declaring classes', () => {
|
||||||
expect(emitStmt(new o.ClassStmt('SomeClass', null, [], [], null, [
|
expect(emitStmt(new o.ClassStmt('SomeClass', null !, [], [], null !, [
|
||||||
]))).toEqual(['function SomeClass() {', '}'].join('\n'));
|
]))).toEqual(['function SomeClass() {', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt('SomeClass', null, [], [], null, []), ['SomeClass']))
|
expect(emitStmt(new o.ClassStmt('SomeClass', null !, [], [], null !, []), ['SomeClass']))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'function SomeClass() {', '}',
|
'function SomeClass() {', '}',
|
||||||
`Object.defineProperty(exports, 'SomeClass', { get: function() { return SomeClass; }});`
|
`Object.defineProperty(exports, 'SomeClass', { get: function() { return SomeClass; }});`
|
||||||
].join('\n'));
|
].join('\n'));
|
||||||
expect(
|
expect(emitStmt(
|
||||||
emitStmt(new o.ClassStmt('SomeClass', o.variable('SomeSuperClass'), [], [], null, [])))
|
new o.ClassStmt('SomeClass', o.variable('SomeSuperClass'), [], [], null !, [])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'function SomeClass() {', '}',
|
'function SomeClass() {', '}',
|
||||||
'SomeClass.prototype = Object.create(SomeSuperClass.prototype);'
|
'SomeClass.prototype = Object.create(SomeSuperClass.prototype);'
|
||||||
@ -241,23 +242,24 @@ export function main() {
|
|||||||
|
|
||||||
it('should support declaring constructors', () => {
|
it('should support declaring constructors', () => {
|
||||||
const superCall = o.SUPER_EXPR.callFn([o.variable('someParam')]).toStmt();
|
const superCall = o.SUPER_EXPR.callFn([o.variable('someParam')]).toStmt();
|
||||||
expect(emitStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
new o.ClassStmt('SomeClass', null, [], [], new o.ClassMethod(null, [], []), [])))
|
'SomeClass', null !, [], [], new o.ClassMethod(null !, [], []), [])))
|
||||||
.toEqual(['function SomeClass() {', '}'].join('\n'));
|
.toEqual(['function SomeClass() {', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [],
|
'SomeClass', null !, [], [],
|
||||||
new o.ClassMethod(null, [new o.FnParam('someParam')], []), [])))
|
new o.ClassMethod(null !, [new o.FnParam('someParam')], []), [])))
|
||||||
.toEqual(['function SomeClass(someParam) {', '}'].join('\n'));
|
.toEqual(['function SomeClass(someParam) {', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', o.variable('SomeSuperClass'), [], [],
|
'SomeClass', o.variable('SomeSuperClass'), [], [],
|
||||||
new o.ClassMethod(null, [], [superCall]), [])))
|
new o.ClassMethod(null !, [], [superCall]), [])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'function SomeClass() {', ' var self = this;',
|
'function SomeClass() {', ' var self = this;',
|
||||||
' SomeSuperClass.call(this, someParam);', '}',
|
' SomeSuperClass.call(this, someParam);', '}',
|
||||||
'SomeClass.prototype = Object.create(SomeSuperClass.prototype);'
|
'SomeClass.prototype = Object.create(SomeSuperClass.prototype);'
|
||||||
].join('\n'));
|
].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(
|
||||||
'SomeClass', null, [], [], new o.ClassMethod(null, [], [callSomeMethod]), [])))
|
emitStmt(new o.ClassStmt(
|
||||||
|
'SomeClass', null !, [], [], new o.ClassMethod(null !, [], [callSomeMethod]), [])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'function SomeClass() {', ' var self = this;', ' self.someMethod();', '}'
|
'function SomeClass() {', ' var self = this;', ' self.someMethod();', '}'
|
||||||
].join('\n'));
|
].join('\n'));
|
||||||
@ -265,14 +267,14 @@ export function main() {
|
|||||||
|
|
||||||
it('should support declaring getters', () => {
|
it('should support declaring getters', () => {
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [new o.ClassGetter('someGetter', [])], null, [])))
|
'SomeClass', null !, [], [new o.ClassGetter('someGetter', [])], null !, [])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'function SomeClass() {', '}',
|
'function SomeClass() {', '}',
|
||||||
`Object.defineProperty(SomeClass.prototype, 'someGetter', { get: function() {`, `}});`
|
`Object.defineProperty(SomeClass.prototype, 'someGetter', { get: function() {`, `}});`
|
||||||
].join('\n'));
|
].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [new o.ClassGetter('someGetter', [callSomeMethod])], null,
|
'SomeClass', null !, [], [new o.ClassGetter('someGetter', [callSomeMethod])],
|
||||||
[])))
|
null !, [])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'function SomeClass() {', '}',
|
'function SomeClass() {', '}',
|
||||||
`Object.defineProperty(SomeClass.prototype, 'someGetter', { get: function() {`,
|
`Object.defineProperty(SomeClass.prototype, 'someGetter', { get: function() {`,
|
||||||
@ -282,19 +284,19 @@ export function main() {
|
|||||||
|
|
||||||
it('should support methods', () => {
|
it('should support methods', () => {
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [], null, [new o.ClassMethod('someMethod', [], [])])))
|
'SomeClass', null !, [], [], null !, [new o.ClassMethod('someMethod', [], [])])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'function SomeClass() {', '}', 'SomeClass.prototype.someMethod = function() {', '};'
|
'function SomeClass() {', '}', 'SomeClass.prototype.someMethod = function() {', '};'
|
||||||
].join('\n'));
|
].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [], null,
|
'SomeClass', null !, [], [], null !,
|
||||||
[new o.ClassMethod('someMethod', [new o.FnParam('someParam')], [])])))
|
[new o.ClassMethod('someMethod', [new o.FnParam('someParam')], [])])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'function SomeClass() {', '}',
|
'function SomeClass() {', '}',
|
||||||
'SomeClass.prototype.someMethod = function(someParam) {', '};'
|
'SomeClass.prototype.someMethod = function(someParam) {', '};'
|
||||||
].join('\n'));
|
].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [], null,
|
'SomeClass', null !, [], [], null !,
|
||||||
[new o.ClassMethod('someMethod', [], [callSomeMethod])])))
|
[new o.ClassMethod('someMethod', [], [callSomeMethod])])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'function SomeClass() {', '}', 'SomeClass.prototype.someMethod = function() {',
|
'function SomeClass() {', '}', 'SomeClass.prototype.someMethod = function() {',
|
||||||
|
@ -52,7 +52,7 @@ export function main() {
|
|||||||
.addMapping(3, 'a.js', 5, 2);
|
.addMapping(3, 'a.js', 5, 2);
|
||||||
|
|
||||||
// Generated with https://sokra.github.io/source-map-visualization using a TS source map
|
// Generated with https://sokra.github.io/source-map-visualization using a TS source map
|
||||||
expect(map.toJSON().mappings)
|
expect(map.toJSON() !.mappings)
|
||||||
.toEqual(
|
.toEqual(
|
||||||
'AAAA,IAAM,CAAC,GAAe,CAAC,CAAC;AACxB,IAAM,CAAC,GAAG,CAAC,CAAC;AAEZ,EAAE,CAAC,OAAO,CAAC,UAAA,CAAC;IACR,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC;AACvB,CAAC,CAAC,CAAA');
|
'AAAA,IAAM,CAAC,GAAe,CAAC,CAAC;AACxB,IAAM,CAAC,GAAG,CAAC,CAAC;AAEZ,EAAE,CAAC,OAAO,CAAC,UAAA,CAAC;IACR,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC;AACvB,CAAC,CAAC,CAAA');
|
||||||
});
|
});
|
||||||
@ -64,7 +64,7 @@ export function main() {
|
|||||||
.addSource('url.ts', null)
|
.addSource('url.ts', null)
|
||||||
.addLine()
|
.addLine()
|
||||||
.addMapping(0, 'inline.ts', 0, 0)
|
.addMapping(0, 'inline.ts', 0, 0)
|
||||||
.toJSON();
|
.toJSON() !;
|
||||||
|
|
||||||
expect(map.file).toEqual('out.js');
|
expect(map.file).toEqual('out.js');
|
||||||
expect(map.sources).toEqual(['inline.ts', 'url.ts']);
|
expect(map.sources).toEqual(['inline.ts', 'url.ts']);
|
||||||
@ -113,7 +113,7 @@ export function main() {
|
|||||||
|
|
||||||
it('should throw when adding segments without column', () => {
|
it('should throw when adding segments without column', () => {
|
||||||
expect(() => {
|
expect(() => {
|
||||||
new SourceMapGenerator('out.js').addSource('in.js').addLine().addMapping(null);
|
new SourceMapGenerator('out.js').addSource('in.js').addLine().addMapping(null !);
|
||||||
}).toThrowError('The column in the generated code must be provided');
|
}).toThrowError('The column in the generated code must be provided');
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -17,7 +17,8 @@ export interface SourceLocation {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function originalPositionFor(
|
export function originalPositionFor(
|
||||||
sourceMap: SourceMap, genPosition: {line: number, column: number}): SourceLocation {
|
sourceMap: SourceMap,
|
||||||
|
genPosition: {line: number | null, column: number | null}): SourceLocation {
|
||||||
const smc = new SourceMapConsumer(sourceMap);
|
const smc = new SourceMapConsumer(sourceMap);
|
||||||
// Note: We don't return the original object as it also contains a `name` property
|
// Note: We don't return the original object as it also contains a `name` property
|
||||||
// which is always null and we don't want to include that in our assertions...
|
// which is always null and we don't want to include that in our assertions...
|
||||||
@ -25,7 +26,7 @@ export function originalPositionFor(
|
|||||||
return {line, column, source};
|
return {line, column, source};
|
||||||
}
|
}
|
||||||
|
|
||||||
export function extractSourceMap(source: string): SourceMap {
|
export function extractSourceMap(source: string): SourceMap|null {
|
||||||
let idx = source.lastIndexOf('\n//#');
|
let idx = source.lastIndexOf('\n//#');
|
||||||
if (idx == -1) return null;
|
if (idx == -1) return null;
|
||||||
const smComment = source.slice(idx).trim();
|
const smComment = source.slice(idx).trim();
|
||||||
|
@ -23,8 +23,8 @@ class SimpleJsImportGenerator implements ImportResolver {
|
|||||||
fileNameToModuleName(importedUrlStr: string, moduleUrlStr: string): string {
|
fileNameToModuleName(importedUrlStr: string, moduleUrlStr: string): string {
|
||||||
return importedUrlStr;
|
return importedUrlStr;
|
||||||
}
|
}
|
||||||
getImportAs(symbol: StaticSymbol): StaticSymbol { return null; }
|
getImportAs(symbol: StaticSymbol): StaticSymbol|null { return null; }
|
||||||
getTypeArity(symbol: StaticSymbol): number /*|null*/ { return null; }
|
getTypeArity(symbol: StaticSymbol): number|null { return null; }
|
||||||
}
|
}
|
||||||
|
|
||||||
export function main() {
|
export function main() {
|
||||||
@ -44,12 +44,12 @@ export function main() {
|
|||||||
});
|
});
|
||||||
|
|
||||||
function emitSourceMap(
|
function emitSourceMap(
|
||||||
stmt: o.Statement | o.Statement[], exportedVars: string[] = null,
|
stmt: o.Statement | o.Statement[], exportedVars: string[] | null = null,
|
||||||
preamble?: string): SourceMap {
|
preamble?: string): SourceMap {
|
||||||
const stmts = Array.isArray(stmt) ? stmt : [stmt];
|
const stmts = Array.isArray(stmt) ? stmt : [stmt];
|
||||||
const source = emitter.emitStatements(
|
const source = emitter.emitStatements(
|
||||||
someSourceFilePath, someGenFilePath, stmts, exportedVars || [], preamble);
|
someSourceFilePath, someGenFilePath, stmts, exportedVars || [], preamble);
|
||||||
return extractSourceMap(source);
|
return extractSourceMap(source) !;
|
||||||
}
|
}
|
||||||
|
|
||||||
describe('source maps', () => {
|
describe('source maps', () => {
|
||||||
|
@ -30,8 +30,8 @@ class SimpleJsImportGenerator implements ImportResolver {
|
|||||||
fileNameToModuleName(importedUrlStr: string, moduleUrlStr: string): string {
|
fileNameToModuleName(importedUrlStr: string, moduleUrlStr: string): string {
|
||||||
return importedUrlStr;
|
return importedUrlStr;
|
||||||
}
|
}
|
||||||
getImportAs(symbol: StaticSymbol): StaticSymbol { return null; }
|
getImportAs(symbol: StaticSymbol): StaticSymbol|null { return null; }
|
||||||
getTypeArity(symbol: StaticSymbol): number /*|null*/ { return null; }
|
getTypeArity(symbol: StaticSymbol): number|null { return null; }
|
||||||
}
|
}
|
||||||
|
|
||||||
export function main() {
|
export function main() {
|
||||||
@ -47,11 +47,11 @@ export function main() {
|
|||||||
beforeEach(() => {
|
beforeEach(() => {
|
||||||
importResolver = new SimpleJsImportGenerator();
|
importResolver = new SimpleJsImportGenerator();
|
||||||
emitter = new TypeScriptEmitter(importResolver);
|
emitter = new TypeScriptEmitter(importResolver);
|
||||||
someVar = o.variable('someVar');
|
someVar = o.variable('someVar', null, null);
|
||||||
});
|
});
|
||||||
|
|
||||||
function emitStmt(
|
function emitStmt(
|
||||||
stmt: o.Statement | o.Statement[], exportedVars: string[] = null,
|
stmt: o.Statement | o.Statement[], exportedVars: string[] | null = null,
|
||||||
preamble?: string): string {
|
preamble?: string): string {
|
||||||
const stmts = Array.isArray(stmt) ? stmt : [stmt];
|
const stmts = Array.isArray(stmt) ? stmt : [stmt];
|
||||||
const source = emitter.emitStatements(
|
const source = emitter.emitStatements(
|
||||||
@ -310,31 +310,32 @@ export function main() {
|
|||||||
|
|
||||||
|
|
||||||
it('should support declaring classes', () => {
|
it('should support declaring classes', () => {
|
||||||
expect(emitStmt(new o.ClassStmt('SomeClass', null, [], [], null, [
|
expect(emitStmt(new o.ClassStmt('SomeClass', null !, [], [], null !, [
|
||||||
]))).toEqual(['class SomeClass {', '}'].join('\n'));
|
]))).toEqual(['class SomeClass {', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt('SomeClass', null, [], [], null, []), ['SomeClass']))
|
expect(emitStmt(new o.ClassStmt('SomeClass', null !, [], [], null !, []), ['SomeClass']))
|
||||||
.toEqual(['export class SomeClass {', '}'].join('\n'));
|
.toEqual(['export class SomeClass {', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt('SomeClass', o.variable('SomeSuperClass'), [], [], null, [
|
expect(emitStmt(new o.ClassStmt('SomeClass', o.variable('SomeSuperClass'), [], [], null !, [
|
||||||
]))).toEqual(['class SomeClass extends SomeSuperClass {', '}'].join('\n'));
|
]))).toEqual(['class SomeClass extends SomeSuperClass {', '}'].join('\n'));
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should support declaring constructors', () => {
|
it('should support declaring constructors', () => {
|
||||||
const superCall = o.SUPER_EXPR.callFn([o.variable('someParam')]).toStmt();
|
const superCall = o.SUPER_EXPR.callFn([o.variable('someParam')]).toStmt();
|
||||||
expect(emitStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
new o.ClassStmt('SomeClass', null, [], [], new o.ClassMethod(null, [], []), [])))
|
'SomeClass', null !, [], [], new o.ClassMethod(null !, [], []), [])))
|
||||||
.toEqual(['class SomeClass {', ' constructor() {', ' }', '}'].join('\n'));
|
.toEqual(['class SomeClass {', ' constructor() {', ' }', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [],
|
'SomeClass', null !, [], [],
|
||||||
new o.ClassMethod(null, [new o.FnParam('someParam', o.INT_TYPE)], []), [])))
|
new o.ClassMethod(null !, [new o.FnParam('someParam', o.INT_TYPE)], []), [])))
|
||||||
.toEqual(
|
.toEqual(
|
||||||
['class SomeClass {', ' constructor(someParam:number) {', ' }', '}'].join('\n'));
|
['class SomeClass {', ' constructor(someParam:number) {', ' }', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [], new o.ClassMethod(null, [], [superCall]), [])))
|
'SomeClass', null !, [], [], new o.ClassMethod(null !, [], [superCall]), [])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'class SomeClass {', ' constructor() {', ' super(someParam);', ' }', '}'
|
'class SomeClass {', ' constructor() {', ' super(someParam);', ' }', '}'
|
||||||
].join('\n'));
|
].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(
|
||||||
'SomeClass', null, [], [], new o.ClassMethod(null, [], [callSomeMethod]), [])))
|
emitStmt(new o.ClassStmt(
|
||||||
|
'SomeClass', null !, [], [], new o.ClassMethod(null !, [], [callSomeMethod]), [])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'class SomeClass {', ' constructor() {', ' this.someMethod();', ' }', '}'
|
'class SomeClass {', ' constructor() {', ' this.someMethod();', ' }', '}'
|
||||||
].join('\n'));
|
].join('\n'));
|
||||||
@ -342,56 +343,57 @@ export function main() {
|
|||||||
|
|
||||||
it('should support declaring fields', () => {
|
it('should support declaring fields', () => {
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [new o.ClassField('someField')], [], null, [])))
|
'SomeClass', null !, [new o.ClassField('someField')], [], null !, [])))
|
||||||
.toEqual(['class SomeClass {', ' someField:any;', '}'].join('\n'));
|
.toEqual(['class SomeClass {', ' someField:any;', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(
|
||||||
'SomeClass', null, [new o.ClassField('someField', o.INT_TYPE)], [], null, [])))
|
emitStmt(new o.ClassStmt(
|
||||||
|
'SomeClass', null !, [new o.ClassField('someField', o.INT_TYPE)], [], null !, [])))
|
||||||
.toEqual(['class SomeClass {', ' someField:number;', '}'].join('\n'));
|
.toEqual(['class SomeClass {', ' someField:number;', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null,
|
'SomeClass', null !,
|
||||||
[new o.ClassField('someField', o.INT_TYPE, [o.StmtModifier.Private])], [], null,
|
[new o.ClassField('someField', o.INT_TYPE, [o.StmtModifier.Private])], [],
|
||||||
[])))
|
null !, [])))
|
||||||
.toEqual(['class SomeClass {', ' /*private*/ someField:number;', '}'].join('\n'));
|
.toEqual(['class SomeClass {', ' /*private*/ someField:number;', '}'].join('\n'));
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should support declaring getters', () => {
|
it('should support declaring getters', () => {
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [new o.ClassGetter('someGetter', [])], null, [])))
|
'SomeClass', null !, [], [new o.ClassGetter('someGetter', [])], null !, [])))
|
||||||
.toEqual(['class SomeClass {', ' get someGetter():any {', ' }', '}'].join('\n'));
|
.toEqual(['class SomeClass {', ' get someGetter():any {', ' }', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [new o.ClassGetter('someGetter', [], o.INT_TYPE)], null,
|
'SomeClass', null !, [], [new o.ClassGetter('someGetter', [], o.INT_TYPE)],
|
||||||
[])))
|
null !, [])))
|
||||||
.toEqual(['class SomeClass {', ' get someGetter():number {', ' }', '}'].join('\n'));
|
.toEqual(['class SomeClass {', ' get someGetter():number {', ' }', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [new o.ClassGetter('someGetter', [callSomeMethod])], null,
|
'SomeClass', null !, [], [new o.ClassGetter('someGetter', [callSomeMethod])],
|
||||||
[])))
|
null !, [])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'class SomeClass {', ' get someGetter():any {', ' this.someMethod();', ' }', '}'
|
'class SomeClass {', ' get someGetter():any {', ' this.someMethod();', ' }', '}'
|
||||||
].join('\n'));
|
].join('\n'));
|
||||||
expect(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
emitStmt(new o.ClassStmt(
|
'SomeClass', null !, [],
|
||||||
'SomeClass', null, [],
|
[new o.ClassGetter('someGetter', [], null !, [o.StmtModifier.Private])], null !,
|
||||||
[new o.ClassGetter('someGetter', [], null, [o.StmtModifier.Private])], null, [])))
|
[])))
|
||||||
.toEqual(
|
.toEqual(
|
||||||
['class SomeClass {', ' private get someGetter():any {', ' }', '}'].join('\n'));
|
['class SomeClass {', ' private get someGetter():any {', ' }', '}'].join('\n'));
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should support methods', () => {
|
it('should support methods', () => {
|
||||||
expect(emitStmt(new o.ClassStmt('SomeClass', null, [], [], null, [
|
expect(emitStmt(new o.ClassStmt('SomeClass', null !, [], [], null !, [
|
||||||
new o.ClassMethod('someMethod', [], [])
|
new o.ClassMethod('someMethod', [], [])
|
||||||
]))).toEqual(['class SomeClass {', ' someMethod():void {', ' }', '}'].join('\n'));
|
]))).toEqual(['class SomeClass {', ' someMethod():void {', ' }', '}'].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt('SomeClass', null, [], [], null, [
|
expect(emitStmt(new o.ClassStmt('SomeClass', null !, [], [], null !, [
|
||||||
new o.ClassMethod('someMethod', [], [], o.INT_TYPE)
|
new o.ClassMethod('someMethod', [], [], o.INT_TYPE)
|
||||||
]))).toEqual(['class SomeClass {', ' someMethod():number {', ' }', '}'].join('\n'));
|
]))).toEqual(['class SomeClass {', ' someMethod():number {', ' }', '}'].join('\n'));
|
||||||
expect(
|
expect(
|
||||||
emitStmt(new o.ClassStmt(
|
emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [], null,
|
'SomeClass', null !, [], [], null !,
|
||||||
[new o.ClassMethod('someMethod', [new o.FnParam('someParam', o.INT_TYPE)], [])])))
|
[new o.ClassMethod('someMethod', [new o.FnParam('someParam', o.INT_TYPE)], [])])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'class SomeClass {', ' someMethod(someParam:number):void {', ' }', '}'
|
'class SomeClass {', ' someMethod(someParam:number):void {', ' }', '}'
|
||||||
].join('\n'));
|
].join('\n'));
|
||||||
expect(emitStmt(new o.ClassStmt(
|
expect(emitStmt(new o.ClassStmt(
|
||||||
'SomeClass', null, [], [], null,
|
'SomeClass', null !, [], [], null !,
|
||||||
[new o.ClassMethod('someMethod', [], [callSomeMethod])])))
|
[new o.ClassMethod('someMethod', [], [callSomeMethod])])))
|
||||||
.toEqual([
|
.toEqual([
|
||||||
'class SomeClass {', ' someMethod():void {', ' this.someMethod();', ' }', '}'
|
'class SomeClass {', ' someMethod():void {', ' this.someMethod();', ' }', '}'
|
||||||
@ -453,7 +455,7 @@ export function main() {
|
|||||||
|
|
||||||
it('should support combined types', () => {
|
it('should support combined types', () => {
|
||||||
const writeVarExpr = o.variable('a').set(o.NULL_EXPR);
|
const writeVarExpr = o.variable('a').set(o.NULL_EXPR);
|
||||||
expect(emitStmt(writeVarExpr.toDeclStmt(new o.ArrayType(null))))
|
expect(emitStmt(writeVarExpr.toDeclStmt(new o.ArrayType(null !))))
|
||||||
.toEqual('var a:any[] = (null as any);');
|
.toEqual('var a:any[] = (null as any);');
|
||||||
expect(emitStmt(writeVarExpr.toDeclStmt(new o.ArrayType(o.INT_TYPE))))
|
expect(emitStmt(writeVarExpr.toDeclStmt(new o.ArrayType(o.INT_TYPE))))
|
||||||
.toEqual('var a:number[] = (null as any);');
|
.toEqual('var a:number[] = (null as any);');
|
||||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user