86 lines
2.9 KiB
TypeScript
Raw Normal View History

/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* 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
*/
import {StaticSymbol} from '../aot/static_symbol';
import {CompileIdentifierMetadata} from '../compile_metadata';
import {EmitterVisitorContext, OutputEmitter} from './abstract_emitter';
import {AbstractJsEmitterVisitor} from './abstract_js_emitter';
import * as o from './output_ast';
export class JavaScriptEmitter implements OutputEmitter {
emitStatements(
srcFilePath: string, genFilePath: string, stmts: o.Statement[],
preamble: string = ''): string {
const converter = new JsEmitterVisitor();
const ctx = EmitterVisitorContext.createRoot();
converter.visitAllStatements(stmts, ctx);
const preambleLines = preamble ? preamble.split('\n') : [];
converter.importsWithPrefixes.forEach((prefix, importedModuleName) => {
// Note: can't write the real word for import as it screws up system.js auto detection...
preambleLines.push(
`var ${prefix} = req` +
`uire('${importedModuleName}');`);
});
const sm =
ctx.toSourceMapGenerator(srcFilePath, genFilePath, preambleLines.length).toJsComment();
const lines = [...preambleLines, ctx.toSource(), sm];
if (sm) {
// always add a newline at the end, as some tools have bugs without it.
lines.push('');
}
return lines.join('\n');
}
}
class JsEmitterVisitor extends AbstractJsEmitterVisitor {
importsWithPrefixes = new Map<string, string>();
visitExternalExpr(ast: o.ExternalExpr, ctx: EmitterVisitorContext): any {
const {name, moduleName} = ast.value;
if (moduleName) {
let prefix = this.importsWithPrefixes.get(moduleName);
2017-03-02 09:37:01 -08:00
if (prefix == null) {
prefix = `i${this.importsWithPrefixes.size}`;
this.importsWithPrefixes.set(moduleName, prefix);
}
ctx.print(ast, `${prefix}.`);
}
ctx.print(ast, name !);
return null;
}
visitDeclareVarStmt(stmt: o.DeclareVarStmt, ctx: EmitterVisitorContext): any {
super.visitDeclareVarStmt(stmt, ctx);
if (stmt.hasModifier(o.StmtModifier.Exported)) {
ctx.println(stmt, exportVar(stmt.name));
}
return null;
}
visitDeclareFunctionStmt(stmt: o.DeclareFunctionStmt, ctx: EmitterVisitorContext): any {
super.visitDeclareFunctionStmt(stmt, ctx);
if (stmt.hasModifier(o.StmtModifier.Exported)) {
ctx.println(stmt, exportVar(stmt.name));
}
return null;
}
visitDeclareClassStmt(stmt: o.ClassStmt, ctx: EmitterVisitorContext): any {
super.visitDeclareClassStmt(stmt, ctx);
if (stmt.hasModifier(o.StmtModifier.Exported)) {
ctx.println(stmt, exportVar(stmt.name));
}
return null;
}
}
function exportVar(varName: string): string {
return `Object.defineProperty(exports, '${varName}', { get: function() { return ${varName}; }});`;
}