Merge branch 'master' into FixAbsoluteTripleSlashCompletions

This commit is contained in:
Arthur Ozga
2016-09-30 15:56:47 -07:00
869 changed files with 5102 additions and 4174 deletions
+3 -3
View File
@@ -2592,7 +2592,7 @@ namespace ts {
}
// Currently, we only support generators that were originally async function bodies.
if (asteriskToken && node.emitFlags & NodeEmitFlags.AsyncFunctionBody) {
if (asteriskToken && getEmitFlags(node) & EmitFlags.AsyncFunctionBody) {
transformFlags |= TransformFlags.AssertGenerator;
}
@@ -2667,7 +2667,7 @@ namespace ts {
// down-level generator.
// Currently we do not support transforming any other generator fucntions
// down level.
if (asteriskToken && node.emitFlags & NodeEmitFlags.AsyncFunctionBody) {
if (asteriskToken && getEmitFlags(node) & EmitFlags.AsyncFunctionBody) {
transformFlags |= TransformFlags.AssertGenerator;
}
}
@@ -2698,7 +2698,7 @@ namespace ts {
// down-level generator.
// Currently we do not support transforming any other generator fucntions
// down level.
if (asteriskToken && node.emitFlags & NodeEmitFlags.AsyncFunctionBody) {
if (asteriskToken && getEmitFlags(node) & EmitFlags.AsyncFunctionBody) {
transformFlags |= TransformFlags.AssertGenerator;
}
+7 -4
View File
@@ -9421,8 +9421,8 @@ namespace ts {
let container = getSuperContainer(node, /*stopOnFunctions*/ true);
let needToCaptureLexicalThis = false;
// adjust the container reference in case if super is used inside arrow functions with arbitrarily deep nesting
if (!isCallExpression) {
// adjust the container reference in case if super is used inside arrow functions with arbitrary deep nesting
while (container && container.kind === SyntaxKind.ArrowFunction) {
container = getSuperContainer(container, /*stopOnFunctions*/ true);
needToCaptureLexicalThis = languageVersion < ScriptTarget.ES6;
@@ -14439,6 +14439,7 @@ namespace ts {
// constructors of derived classes must contain at least one super call somewhere in their function body.
const containingClassDecl = <ClassDeclaration>node.parent;
if (getClassExtendsHeritageClauseElement(containingClassDecl)) {
captureLexicalThis(node.parent, containingClassDecl);
const classExtendsNull = classDeclarationExtendsNull(containingClassDecl);
const superCall = getSuperCallInConstructor(node);
if (superCall) {
@@ -17713,9 +17714,11 @@ namespace ts {
}
function checkGrammarModuleElementContext(node: Statement, errorMessage: DiagnosticMessage): boolean {
if (node.parent.kind !== SyntaxKind.SourceFile && node.parent.kind !== SyntaxKind.ModuleBlock && node.parent.kind !== SyntaxKind.ModuleDeclaration) {
return grammarErrorOnFirstToken(node, errorMessage);
const isInAppropriateContext = node.parent.kind === SyntaxKind.SourceFile || node.parent.kind === SyntaxKind.ModuleBlock || node.parent.kind === SyntaxKind.ModuleDeclaration;
if (!isInAppropriateContext) {
grammarErrorOnFirstToken(node, errorMessage);
}
return !isInAppropriateContext;
}
function checkExportSpecifier(node: ExportSpecifier) {
@@ -17756,7 +17759,7 @@ namespace ts {
checkExpressionCached(node.expression);
}
checkExternalModuleExports(<SourceFile | ModuleDeclaration>container);
checkExternalModuleExports(container);
if (node.isExportEquals && !isInAmbientContext(node)) {
if (modulekind === ModuleKind.ES6) {
+24 -29
View File
@@ -5,7 +5,7 @@ namespace ts {
export interface CommentWriter {
reset(): void;
setSourceFile(sourceFile: SourceFile): void;
emitNodeWithComments(node: Node, emitCallback: (node: Node) => void): void;
emitNodeWithComments(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void): void;
emitBodyWithDetachedComments(node: Node, detachedRange: TextRange, emitCallback: (node: Node) => void): void;
emitTrailingCommentsOfPosition(pos: number): void;
}
@@ -34,22 +34,24 @@ namespace ts {
emitTrailingCommentsOfPosition,
};
function emitNodeWithComments(node: Node, emitCallback: (node: Node) => void) {
function emitNodeWithComments(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void) {
if (disabled) {
emitCallback(node);
emitCallback(emitContext, node);
return;
}
if (node) {
const { pos, end } = node.commentRange || node;
const emitFlags = node.emitFlags;
const { pos, end } = getCommentRange(node);
const emitFlags = getEmitFlags(node);
if ((pos < 0 && end < 0) || (pos === end)) {
// Both pos and end are synthesized, so just emit the node without comments.
if (emitFlags & NodeEmitFlags.NoNestedComments) {
disableCommentsAndEmit(node, emitCallback);
if (emitFlags & EmitFlags.NoNestedComments) {
disabled = true;
emitCallback(emitContext, node);
disabled = false;
}
else {
emitCallback(node);
emitCallback(emitContext, node);
}
}
else {
@@ -58,8 +60,8 @@ namespace ts {
}
const isEmittedNode = node.kind !== SyntaxKind.NotEmittedStatement;
const skipLeadingComments = pos < 0 || (emitFlags & NodeEmitFlags.NoLeadingComments) !== 0;
const skipTrailingComments = end < 0 || (emitFlags & NodeEmitFlags.NoTrailingComments) !== 0;
const skipLeadingComments = pos < 0 || (emitFlags & EmitFlags.NoLeadingComments) !== 0;
const skipTrailingComments = end < 0 || (emitFlags & EmitFlags.NoTrailingComments) !== 0;
// Emit leading comments if the position is not synthesized and the node
// has not opted out from emitting leading comments.
@@ -90,11 +92,13 @@ namespace ts {
performance.measure("commentTime", "preEmitNodeWithComment");
}
if (emitFlags & NodeEmitFlags.NoNestedComments) {
disableCommentsAndEmit(node, emitCallback);
if (emitFlags & EmitFlags.NoNestedComments) {
disabled = true;
emitCallback(emitContext, node);
disabled = false;
}
else {
emitCallback(node);
emitCallback(emitContext, node);
}
if (extendedDiagnostics) {
@@ -125,9 +129,9 @@ namespace ts {
}
const { pos, end } = detachedRange;
const emitFlags = node.emitFlags;
const skipLeadingComments = pos < 0 || (emitFlags & NodeEmitFlags.NoLeadingComments) !== 0;
const skipTrailingComments = disabled || end < 0 || (emitFlags & NodeEmitFlags.NoTrailingComments) !== 0;
const emitFlags = getEmitFlags(node);
const skipLeadingComments = pos < 0 || (emitFlags & EmitFlags.NoLeadingComments) !== 0;
const skipTrailingComments = disabled || end < 0 || (emitFlags & EmitFlags.NoTrailingComments) !== 0;
if (!skipLeadingComments) {
emitDetachedCommentsAndUpdateCommentsInfo(detachedRange);
@@ -137,8 +141,10 @@ namespace ts {
performance.measure("commentTime", "preEmitBodyWithDetachedComments");
}
if (emitFlags & NodeEmitFlags.NoNestedComments) {
disableCommentsAndEmit(node, emitCallback);
if (emitFlags & EmitFlags.NoNestedComments && !disabled) {
disabled = true;
emitCallback(node);
disabled = false;
}
else {
emitCallback(node);
@@ -284,17 +290,6 @@ namespace ts {
detachedCommentsInfo = undefined;
}
function disableCommentsAndEmit(node: Node, emitCallback: (node: Node) => void): void {
if (disabled) {
emitCallback(node);
}
else {
disabled = true;
emitCallback(node);
disabled = false;
}
}
function hasDetachedComments(pos: number) {
return detachedCommentsInfo !== undefined && lastOrUndefined(detachedCommentsInfo).nodePos === pos;
}
+66 -1
View File
@@ -840,6 +840,72 @@ namespace ts {
};
}
/**
* High-order function, creates a function that executes a function composition.
* For example, `chain(a, b)` is the equivalent of `x => ((a', b') => y => b'(a'(y)))(a(x), b(x))`
*
* @param args The functions to chain.
*/
export function chain<T, U>(...args: ((t: T) => (u: U) => U)[]): (t: T) => (u: U) => U;
export function chain<T, U>(a: (t: T) => (u: U) => U, b: (t: T) => (u: U) => U, c: (t: T) => (u: U) => U, d: (t: T) => (u: U) => U, e: (t: T) => (u: U) => U): (t: T) => (u: U) => U {
if (e) {
const args: ((t: T) => (u: U) => U)[] = [];
for (let i = 0; i < arguments.length; i++) {
args[i] = arguments[i];
}
return t => compose(...map(args, f => f(t)));
}
else if (d) {
return t => compose(a(t), b(t), c(t), d(t));
}
else if (c) {
return t => compose(a(t), b(t), c(t));
}
else if (b) {
return t => compose(a(t), b(t));
}
else if (a) {
return t => compose(a(t));
}
else {
return t => u => u;
}
}
/**
* High-order function, composes functions. Note that functions are composed inside-out;
* for example, `compose(a, b)` is the equivalent of `x => b(a(x))`.
*
* @param args The functions to compose.
*/
export function compose<T>(...args: ((t: T) => T)[]): (t: T) => T;
export function compose<T>(a: (t: T) => T, b: (t: T) => T, c: (t: T) => T, d: (t: T) => T, e: (t: T) => T): (t: T) => T {
if (e) {
const args: ((t: T) => T)[] = [];
for (let i = 0; i < arguments.length; i++) {
args[i] = arguments[i];
}
return t => reduceLeft<(t: T) => T, T>(args, (u, f) => f(u), t);
}
else if (d) {
return t => d(c(b(a(t))));
}
else if (c) {
return t => c(b(a(t)));
}
else if (b) {
return t => b(a(t));
}
else if (a) {
return t => a(t);
}
else {
return t => t;
}
}
function formatStringFromArgs(text: string, args: { [index: number]: any; }, baseIndex?: number): string {
baseIndex = baseIndex || 0;
@@ -1790,7 +1856,6 @@ namespace ts {
this.transformFlags = TransformFlags.None;
this.parent = undefined;
this.original = undefined;
this.transformId = 0;
}
export let objectAllocator: ObjectAllocator = {
+157 -246
View File
@@ -206,10 +206,8 @@ const _super = (function (geti, seti) {
const sourceMap = createSourceMapWriter(host, writer);
const {
emitStart,
emitEnd,
emitTokenStart,
emitTokenEnd
emitNodeWithSourceMap,
emitTokenWithSourceMap
} = sourceMap;
const comments = createCommentWriter(host, writer, sourceMap);
@@ -234,36 +232,27 @@ const _super = (function (geti, seti) {
let isOwnFileEmit: boolean;
let emitSkipped = false;
performance.mark("beforeTransform");
const sourceFiles = getSourceFilesToEmit(host, targetSourceFile);
// Transform the source files
const transformed = transformFiles(
resolver,
host,
getSourceFilesToEmit(host, targetSourceFile),
transformers);
performance.mark("beforeTransform");
const {
transformed,
emitNodeWithSubstitution,
emitNodeWithNotification
} = transformFiles(resolver, host, sourceFiles, transformers);
performance.measure("transformTime", "beforeTransform");
// Extract helpers from the result
const {
getTokenSourceMapRange,
isSubstitutionEnabled,
isEmitNotificationEnabled,
onSubstituteNode,
onEmitNode
} = transformed;
performance.mark("beforePrint");
// Emit each output file
forEachTransformedEmitFile(host, transformed.getSourceFiles(), emitFile, emitOnlyDtsFiles);
// Clean up after transformation
transformed.dispose();
performance.mark("beforePrint");
forEachTransformedEmitFile(host, transformed, emitFile, emitOnlyDtsFiles);
performance.measure("printTime", "beforePrint");
// Clean up emit nodes on parse tree
for (const sourceFile of sourceFiles) {
disposeEmitNodes(sourceFile);
}
return {
emitSkipped,
diagnostics: emitterDiagnostics.getDiagnostics(),
@@ -358,154 +347,137 @@ const _super = (function (geti, seti) {
currentFileIdentifiers = node.identifiers;
sourceMap.setSourceFile(node);
comments.setSourceFile(node);
emitNodeWithNotification(node, emitWorker);
pipelineEmitWithNotification(EmitContext.SourceFile, node);
}
/**
* Emits a node.
*/
function emit(node: Node) {
emitNodeWithNotification(node, emitWithComments);
}
/**
* Emits a node with comments.
*
* NOTE: Do not call this method directly. It is part of the emit pipeline
* and should only be called indirectly from emit.
*/
function emitWithComments(node: Node) {
emitNodeWithComments(node, emitWithSourceMap);
pipelineEmitWithNotification(EmitContext.Unspecified, node);
}
/**
* Emits a node with source maps.
*
* NOTE: Do not call this method directly. It is part of the emit pipeline
* and should only be called indirectly from emitWithComments.
* Emits an IdentifierName.
*/
function emitWithSourceMap(node: Node) {
emitNodeWithSourceMap(node, emitWorker);
}
function emitIdentifierName(node: Identifier) {
if (node) {
emitNodeWithNotification(node, emitIdentifierNameWithComments);
}
}
function emitIdentifierNameWithComments(node: Identifier) {
emitNodeWithComments(node, emitWorker);
pipelineEmitWithNotification(EmitContext.IdentifierName, node);
}
/**
* Emits an expression node.
*/
function emitExpression(node: Expression) {
emitNodeWithNotification(node, emitExpressionWithComments);
pipelineEmitWithNotification(EmitContext.Expression, node);
}
/**
* Emits an expression with comments.
* Emits a node with possible notification.
*
* NOTE: Do not call this method directly. It is part of the emitExpression pipeline
* and should only be called indirectly from emitExpression.
* NOTE: Do not call this method directly. It is part of the emit pipeline
* and should only be called from printSourceFile, emit, emitExpression, or
* emitIdentifierName.
*/
function emitExpressionWithComments(node: Expression) {
emitNodeWithComments(node, emitExpressionWithSourceMap);
function pipelineEmitWithNotification(emitContext: EmitContext, node: Node) {
emitNodeWithNotification(emitContext, node, pipelineEmitWithComments);
}
/**
* Emits an expression with source maps.
* Emits a node with comments.
*
* NOTE: Do not call this method directly. It is part of the emitExpression pipeline
* and should only be called indirectly from emitExpressionWithComments.
* NOTE: Do not call this method directly. It is part of the emit pipeline
* and should only be called indirectly from pipelineEmitWithNotification.
*/
function emitExpressionWithSourceMap(node: Expression) {
emitNodeWithSourceMap(node, emitExpressionWorker);
}
/**
* Emits a node with emit notification if available.
*/
function emitNodeWithNotification(node: Node, emitCallback: (node: Node) => void) {
if (node) {
if (isEmitNotificationEnabled(node)) {
onEmitNode(node, emitCallback);
}
else {
emitCallback(node);
}
}
}
function emitNodeWithSourceMap(node: Node, emitCallback: (node: Node) => void) {
if (node) {
emitStart(/*range*/ node, /*contextNode*/ node, shouldSkipLeadingSourceMapForNode, shouldSkipSourceMapForChildren, getSourceMapRange);
emitCallback(node);
emitEnd(/*range*/ node, /*contextNode*/ node, shouldSkipTrailingSourceMapForNode, shouldSkipSourceMapForChildren, getSourceMapRange);
}
}
function getSourceMapRange(node: Node) {
return node.sourceMapRange || node;
}
/**
* Determines whether to skip leading comment emit for a node.
*
* We do not emit comments for NotEmittedStatement nodes or any node that has
* NodeEmitFlags.NoLeadingComments.
*
* @param node A Node.
*/
function shouldSkipLeadingCommentsForNode(node: Node) {
return isNotEmittedStatement(node)
|| (node.emitFlags & NodeEmitFlags.NoLeadingComments) !== 0;
}
/**
* Determines whether to skip source map emit for the start position of a node.
*
* We do not emit source maps for NotEmittedStatement nodes or any node that
* has NodeEmitFlags.NoLeadingSourceMap.
*
* @param node A Node.
*/
function shouldSkipLeadingSourceMapForNode(node: Node) {
return isNotEmittedStatement(node)
|| (node.emitFlags & NodeEmitFlags.NoLeadingSourceMap) !== 0;
}
/**
* Determines whether to skip source map emit for the end position of a node.
*
* We do not emit source maps for NotEmittedStatement nodes or any node that
* has NodeEmitFlags.NoTrailingSourceMap.
*
* @param node A Node.
*/
function shouldSkipTrailingSourceMapForNode(node: Node) {
return isNotEmittedStatement(node)
|| (node.emitFlags & NodeEmitFlags.NoTrailingSourceMap) !== 0;
}
/**
* Determines whether to skip source map emit for a node and its children.
*
* We do not emit source maps for a node that has NodeEmitFlags.NoNestedSourceMaps.
*/
function shouldSkipSourceMapForChildren(node: Node) {
return (node.emitFlags & NodeEmitFlags.NoNestedSourceMaps) !== 0;
}
function emitWorker(node: Node): void {
if (tryEmitSubstitute(node, emitWorker, /*isExpression*/ false)) {
function pipelineEmitWithComments(emitContext: EmitContext, node: Node) {
// Do not emit comments for SourceFile
if (emitContext === EmitContext.SourceFile) {
pipelineEmitWithSourceMap(emitContext, node);
return;
}
emitNodeWithComments(emitContext, node, pipelineEmitWithSourceMap);
}
/**
* Emits a node with source maps.
*
* NOTE: Do not call this method directly. It is part of the emit pipeline
* and should only be called indirectly from pipelineEmitWithComments.
*/
function pipelineEmitWithSourceMap(emitContext: EmitContext, node: Node) {
// Do not emit source mappings for SourceFile or IdentifierName
if (emitContext === EmitContext.SourceFile
|| emitContext === EmitContext.IdentifierName) {
pipelineEmitWithSubstitution(emitContext, node);
return;
}
emitNodeWithSourceMap(emitContext, node, pipelineEmitWithSubstitution);
}
/**
* Emits a node with possible substitution.
*
* NOTE: Do not call this method directly. It is part of the emit pipeline
* and should only be called indirectly from pipelineEmitWithSourceMap or
* pipelineEmitInUnspecifiedContext (when picking a more specific context).
*/
function pipelineEmitWithSubstitution(emitContext: EmitContext, node: Node) {
emitNodeWithSubstitution(emitContext, node, pipelineEmitForContext);
}
/**
* Emits a node.
*
* NOTE: Do not call this method directly. It is part of the emit pipeline
* and should only be called indirectly from pipelineEmitWithSubstitution.
*/
function pipelineEmitForContext(emitContext: EmitContext, node: Node): void {
switch (emitContext) {
case EmitContext.SourceFile: return pipelineEmitInSourceFileContext(node);
case EmitContext.IdentifierName: return pipelineEmitInIdentifierNameContext(node);
case EmitContext.Unspecified: return pipelineEmitInUnspecifiedContext(node);
case EmitContext.Expression: return pipelineEmitInExpressionContext(node);
}
}
/**
* Emits a node in the SourceFile EmitContext.
*
* NOTE: Do not call this method directly. It is part of the emit pipeline
* and should only be called indirectly from pipelineEmitForContext.
*/
function pipelineEmitInSourceFileContext(node: Node): void {
const kind = node.kind;
switch (kind) {
// Top-level nodes
case SyntaxKind.SourceFile:
return emitSourceFile(<SourceFile>node);
}
}
/**
* Emits a node in the IdentifierName EmitContext.
*
* NOTE: Do not call this method directly. It is part of the emit pipeline
* and should only be called indirectly from pipelineEmitForContext.
*/
function pipelineEmitInIdentifierNameContext(node: Node): void {
const kind = node.kind;
switch (kind) {
// Identifiers
case SyntaxKind.Identifier:
return emitIdentifier(<Identifier>node);
}
}
/**
* Emits a node in the Unspecified EmitContext.
*
* NOTE: Do not call this method directly. It is part of the emit pipeline
* and should only be called indirectly from pipelineEmitForContext.
*/
function pipelineEmitInUnspecifiedContext(node: Node): void {
const kind = node.kind;
switch (kind) {
// Pseudo-literals
@@ -541,7 +513,8 @@ const _super = (function (geti, seti) {
case SyntaxKind.StringKeyword:
case SyntaxKind.SymbolKeyword:
case SyntaxKind.GlobalKeyword:
return writeTokenNode(node);
writeTokenText(kind);
return;
// Parse tree nodes
@@ -746,25 +719,24 @@ const _super = (function (geti, seti) {
case SyntaxKind.EnumMember:
return emitEnumMember(<EnumMember>node);
// Top-level nodes
case SyntaxKind.SourceFile:
return emitSourceFile(<SourceFile>node);
// JSDoc nodes (ignored)
// Transformation nodes (ignored)
}
// If the node is an expression, try to emit it as an expression with
// substitution.
if (isExpression(node)) {
return emitExpressionWorker(node);
return pipelineEmitWithSubstitution(EmitContext.Expression, node);
}
}
function emitExpressionWorker(node: Node) {
if (tryEmitSubstitute(node, emitExpressionWorker, /*isExpression*/ true)) {
return;
}
/**
* Emits a node in the Expression EmitContext.
*
* NOTE: Do not call this method directly. It is part of the emit pipeline
* and should only be called indirectly from pipelineEmitForContext.
*/
function pipelineEmitInExpressionContext(node: Node): void {
const kind = node.kind;
switch (kind) {
// Literals
@@ -786,7 +758,8 @@ const _super = (function (geti, seti) {
case SyntaxKind.SuperKeyword:
case SyntaxKind.TrueKeyword:
case SyntaxKind.ThisKeyword:
return writeTokenNode(node);
writeTokenText(kind);
return;
// Expressions
case SyntaxKind.ArrayLiteralExpression:
@@ -888,7 +861,7 @@ const _super = (function (geti, seti) {
//
function emitIdentifier(node: Identifier) {
if (node.emitFlags & NodeEmitFlags.UMDDefine) {
if (getEmitFlags(node) & EmitFlags.UMDDefine) {
writeLines(umdHelper);
}
else {
@@ -1161,7 +1134,7 @@ const _super = (function (geti, seti) {
write("{}");
}
else {
const indentedFlag = node.emitFlags & NodeEmitFlags.Indented;
const indentedFlag = getEmitFlags(node) & EmitFlags.Indented;
if (indentedFlag) {
increaseIndent();
}
@@ -1177,24 +1150,22 @@ const _super = (function (geti, seti) {
}
function emitPropertyAccessExpression(node: PropertyAccessExpression) {
if (tryEmitConstantValue(node)) {
return;
}
let indentBeforeDot = false;
let indentAfterDot = false;
if (!(node.emitFlags & NodeEmitFlags.NoIndentation)) {
if (!(getEmitFlags(node) & EmitFlags.NoIndentation)) {
const dotRangeStart = node.expression.end;
const dotRangeEnd = skipTrivia(currentText, node.expression.end) + 1;
const dotToken = <Node>{ kind: SyntaxKind.DotToken, pos: dotRangeStart, end: dotRangeEnd };
indentBeforeDot = needsIndentation(node, node.expression, dotToken);
indentAfterDot = needsIndentation(node, dotToken, node.name);
}
const shouldEmitDotDot = !indentBeforeDot && needsDotDotForPropertyAccess(node.expression);
emitExpression(node.expression);
increaseIndentIf(indentBeforeDot);
const shouldEmitDotDot = !indentBeforeDot && needsDotDotForPropertyAccess(node.expression);
write(shouldEmitDotDot ? ".." : ".");
increaseIndentIf(indentAfterDot);
emit(node.name);
decreaseIndentIf(indentBeforeDot, indentAfterDot);
@@ -1208,19 +1179,17 @@ const _super = (function (geti, seti) {
const text = getLiteralTextOfNode(<LiteralExpression>expression);
return text.indexOf(tokenToString(SyntaxKind.DotToken)) < 0;
}
else {
else if (isPropertyAccessExpression(expression) || isElementAccessExpression(expression)) {
// check if constant enum value is integer
const constantValue = tryGetConstEnumValue(expression);
const constantValue = getConstantValue(expression);
// isFinite handles cases when constantValue is undefined
return isFinite(constantValue) && Math.floor(constantValue) === constantValue;
return isFinite(constantValue)
&& Math.floor(constantValue) === constantValue
&& compilerOptions.removeComments;
}
}
function emitElementAccessExpression(node: ElementAccessExpression) {
if (tryEmitConstantValue(node)) {
return;
}
emitExpression(node.expression);
write("[");
emitExpression(node.argumentExpression);
@@ -1426,7 +1395,7 @@ const _super = (function (geti, seti) {
}
function emitBlockStatements(node: Block) {
if (node.emitFlags & NodeEmitFlags.SingleLine) {
if (getEmitFlags(node) & EmitFlags.SingleLine) {
emitList(node, node.statements, ListFormat.SingleLineBlockStatements);
}
else {
@@ -1630,12 +1599,12 @@ const _super = (function (geti, seti) {
const body = node.body;
if (body) {
if (isBlock(body)) {
const indentedFlag = node.emitFlags & NodeEmitFlags.Indented;
const indentedFlag = getEmitFlags(node) & EmitFlags.Indented;
if (indentedFlag) {
increaseIndent();
}
if (node.emitFlags & NodeEmitFlags.ReuseTempVariableScope) {
if (getEmitFlags(node) & EmitFlags.ReuseTempVariableScope) {
emitSignatureHead(node);
emitBlockFunctionBody(node, body);
}
@@ -1679,7 +1648,7 @@ const _super = (function (geti, seti) {
// * A non-synthesized body's start and end position are on different lines.
// * Any statement in the body starts on a new line.
if (body.emitFlags & NodeEmitFlags.SingleLine) {
if (getEmitFlags(body) & EmitFlags.SingleLine) {
return true;
}
@@ -1750,7 +1719,7 @@ const _super = (function (geti, seti) {
write("class");
emitNodeWithPrefix(" ", node.name, emitIdentifierName);
const indentedFlag = node.emitFlags & NodeEmitFlags.Indented;
const indentedFlag = getEmitFlags(node) & EmitFlags.Indented;
if (indentedFlag) {
increaseIndent();
}
@@ -2083,8 +2052,8 @@ const _super = (function (geti, seti) {
// "comment1" is not considered to be leading comment for node.initializer
// but rather a trailing comment on the previous node.
const initializer = node.initializer;
if (!shouldSkipLeadingCommentsForNode(initializer)) {
const commentRange = initializer.commentRange || initializer;
if ((getEmitFlags(initializer) & EmitFlags.NoLeadingComments) === 0) {
const commentRange = getCommentRange(initializer);
emitTrailingCommentsOfPosition(commentRange.pos);
}
@@ -2156,23 +2125,23 @@ const _super = (function (geti, seti) {
}
function emitHelpers(node: Node) {
const emitFlags = node.emitFlags;
const emitFlags = getEmitFlags(node);
let helpersEmitted = false;
if (emitFlags & NodeEmitFlags.EmitEmitHelpers) {
if (emitFlags & EmitFlags.EmitEmitHelpers) {
helpersEmitted = emitEmitHelpers(currentSourceFile);
}
if (emitFlags & NodeEmitFlags.EmitExportStar) {
if (emitFlags & EmitFlags.EmitExportStar) {
writeLines(exportStarHelper);
helpersEmitted = true;
}
if (emitFlags & NodeEmitFlags.EmitSuperHelper) {
if (emitFlags & EmitFlags.EmitSuperHelper) {
writeLines(superHelper);
helpersEmitted = true;
}
if (emitFlags & NodeEmitFlags.EmitAdvancedSuperHelper) {
if (emitFlags & EmitFlags.EmitAdvancedSuperHelper) {
writeLines(advancedSuperHelper);
helpersEmitted = true;
}
@@ -2294,36 +2263,6 @@ const _super = (function (geti, seti) {
}
}
function tryEmitSubstitute(node: Node, emitNode: (node: Node) => void, isExpression: boolean) {
if (isSubstitutionEnabled(node) && (node.emitFlags & NodeEmitFlags.NoSubstitution) === 0) {
const substitute = onSubstituteNode(node, isExpression);
if (substitute !== node) {
substitute.emitFlags |= NodeEmitFlags.NoSubstitution;
emitNode(substitute);
return true;
}
}
return false;
}
function tryEmitConstantValue(node: PropertyAccessExpression | ElementAccessExpression): boolean {
const constantValue = tryGetConstEnumValue(node);
if (constantValue !== undefined) {
write(String(constantValue));
if (!compilerOptions.removeComments) {
const propertyName = isPropertyAccessExpression(node)
? declarationNameToString(node.name)
: getTextOfNode(node.argumentExpression);
write(` /* ${propertyName} */`);
}
return true;
}
return false;
}
function emitEmbeddedStatement(node: Statement) {
if (isBlock(node)) {
write(" ");
@@ -2447,7 +2386,7 @@ const _super = (function (geti, seti) {
}
if (shouldEmitInterveningComments) {
const commentRange = child.commentRange || child;
const commentRange = getCommentRange(child);
emitTrailingCommentsOfPosition(commentRange.pos);
}
else {
@@ -2503,31 +2442,13 @@ const _super = (function (geti, seti) {
}
function writeToken(token: SyntaxKind, pos: number, contextNode?: Node) {
const tokenStartPos = emitTokenStart(token, pos, contextNode, shouldSkipLeadingSourceMapForToken, getTokenSourceMapRange);
const tokenEndPos = writeTokenText(token, tokenStartPos);
return emitTokenEnd(token, tokenEndPos, contextNode, shouldSkipTrailingSourceMapForToken, getTokenSourceMapRange);
}
function shouldSkipLeadingSourceMapForToken(contextNode: Node) {
return (contextNode.emitFlags & NodeEmitFlags.NoTokenLeadingSourceMaps) !== 0;
}
function shouldSkipTrailingSourceMapForToken(contextNode: Node) {
return (contextNode.emitFlags & NodeEmitFlags.NoTokenTrailingSourceMaps) !== 0;
return emitTokenWithSourceMap(contextNode, token, pos, writeTokenText);
}
function writeTokenText(token: SyntaxKind, pos?: number) {
const tokenString = tokenToString(token);
write(tokenString);
return positionIsSynthesized(pos) ? -1 : pos + tokenString.length;
}
function writeTokenNode(node: Node) {
if (node) {
emitStart(/*range*/ node, /*contextNode*/ node, shouldSkipLeadingSourceMapForNode, shouldSkipSourceMapForChildren, getSourceMapRange);
writeTokenText(node.kind);
emitEnd(/*range*/ node, /*contextNode*/ node, shouldSkipTrailingSourceMapForNode, shouldSkipSourceMapForChildren, getSourceMapRange);
}
return pos < 0 ? pos : pos + tokenString.length;
}
function increaseIndentIf(value: boolean, valueToWriteWhenNotIndenting?: string) {
@@ -2692,16 +2613,6 @@ const _super = (function (geti, seti) {
return getLiteralText(node, currentSourceFile, languageVersion);
}
function tryGetConstEnumValue(node: Node): number {
if (compilerOptions.isolatedModules) {
return undefined;
}
return isPropertyAccessExpression(node) || isElementAccessExpression(node)
? resolver.getConstantValue(<PropertyAccessExpression | ElementAccessExpression>node)
: undefined;
}
function isSingleLineEmptyBlock(block: Block) {
return !block.multiLine
&& block.statements.length === 0
+175 -11
View File
@@ -76,7 +76,7 @@ namespace ts {
// the original node. We also need to exclude specific properties and only include own-
// properties (to skip members already defined on the shared prototype).
const clone = <T>createNode(node.kind, /*location*/ undefined, node.flags);
clone.original = node;
setOriginalNode(clone, node);
for (const key in node) {
if (clone.hasOwnProperty(key) || !node.hasOwnProperty(key)) {
@@ -435,7 +435,7 @@ namespace ts {
export function createPropertyAccess(expression: Expression, name: string | Identifier, location?: TextRange, flags?: NodeFlags) {
const node = <PropertyAccessExpression>createNode(SyntaxKind.PropertyAccessExpression, location, flags);
node.expression = parenthesizeForAccess(expression);
node.emitFlags = NodeEmitFlags.NoIndentation;
(node.emitNode || (node.emitNode = {})).flags |= EmitFlags.NoIndentation;
node.name = typeof name === "string" ? createIdentifier(name) : name;
return node;
}
@@ -444,7 +444,7 @@ namespace ts {
if (node.expression !== expression || node.name !== name) {
const propertyAccess = createPropertyAccess(expression, name, /*location*/ node, node.flags);
// Because we are updating existed propertyAccess we want to inherit its emitFlags instead of using default from createPropertyAccess
propertyAccess.emitFlags = node.emitFlags;
(propertyAccess.emitNode || (propertyAccess.emitNode = {})).flags = getEmitFlags(node);
return updateNode(propertyAccess, node);
}
return node;
@@ -1551,7 +1551,7 @@ namespace ts {
}
else {
const expression = isIdentifier(memberName) ? createPropertyAccess(target, memberName, location) : createElementAccess(target, memberName, location);
expression.emitFlags |= NodeEmitFlags.NoNestedSourceMaps;
(expression.emitNode || (expression.emitNode = {})).flags |= EmitFlags.NoNestedSourceMaps;
return expression;
}
}
@@ -1744,7 +1744,7 @@ namespace ts {
);
// Mark this node as originally an async function
generatorFunc.emitFlags |= NodeEmitFlags.AsyncFunctionBody;
(generatorFunc.emitNode || (generatorFunc.emitNode = {})).flags |= EmitFlags.AsyncFunctionBody;
return createCall(
createHelperName(externalHelpersModuleName, "__awaiter"),
@@ -2222,7 +2222,7 @@ namespace ts {
target.push(startOnNewLine(createStatement(createLiteral("use strict"))));
foundUseStrict = true;
}
if (statement.emitFlags & NodeEmitFlags.CustomPrologue) {
if (getEmitFlags(statement) & EmitFlags.CustomPrologue) {
target.push(visitor ? visitNode(statement, visitor, isStatement) : statement);
}
else {
@@ -2643,14 +2643,178 @@ namespace ts {
export function setOriginalNode<T extends Node>(node: T, original: Node): T {
node.original = original;
if (original) {
const { emitFlags, commentRange, sourceMapRange } = original;
if (emitFlags) node.emitFlags = emitFlags;
if (commentRange) node.commentRange = commentRange;
if (sourceMapRange) node.sourceMapRange = sourceMapRange;
const emitNode = original.emitNode;
if (emitNode) node.emitNode = mergeEmitNode(emitNode, node.emitNode);
}
return node;
}
function mergeEmitNode(sourceEmitNode: EmitNode, destEmitNode: EmitNode) {
const { flags, commentRange, sourceMapRange, tokenSourceMapRanges } = sourceEmitNode;
if (!destEmitNode && (flags || commentRange || sourceMapRange || tokenSourceMapRanges)) destEmitNode = {};
if (flags) destEmitNode.flags = flags;
if (commentRange) destEmitNode.commentRange = commentRange;
if (sourceMapRange) destEmitNode.sourceMapRange = sourceMapRange;
if (tokenSourceMapRanges) destEmitNode.tokenSourceMapRanges = mergeTokenSourceMapRanges(tokenSourceMapRanges, destEmitNode.tokenSourceMapRanges);
return destEmitNode;
}
function mergeTokenSourceMapRanges(sourceRanges: Map<TextRange>, destRanges: Map<TextRange>) {
if (!destRanges) destRanges = createMap<TextRange>();
copyProperties(sourceRanges, destRanges);
return destRanges;
}
/**
* Clears any EmitNode entries from parse-tree nodes.
* @param sourceFile A source file.
*/
export function disposeEmitNodes(sourceFile: SourceFile) {
// During transformation we may need to annotate a parse tree node with transient
// transformation properties. As parse tree nodes live longer than transformation
// nodes, we need to make sure we reclaim any memory allocated for custom ranges
// from these nodes to ensure we do not hold onto entire subtrees just for position
// information. We also need to reset these nodes to a pre-transformation state
// for incremental parsing scenarios so that we do not impact later emit.
sourceFile = getSourceFileOfNode(getParseTreeNode(sourceFile));
const emitNode = sourceFile && sourceFile.emitNode;
const annotatedNodes = emitNode && emitNode.annotatedNodes;
if (annotatedNodes) {
for (const node of annotatedNodes) {
node.emitNode = undefined;
}
}
}
/**
* Associates a node with the current transformation, initializing
* various transient transformation properties.
*
* @param node The node.
*/
function getOrCreateEmitNode(node: Node) {
if (!node.emitNode) {
if (isParseTreeNode(node)) {
// To avoid holding onto transformation artifacts, we keep track of any
// parse tree node we are annotating. This allows us to clean them up after
// all transformations have completed.
if (node.kind === SyntaxKind.SourceFile) {
return node.emitNode = { annotatedNodes: [node] };
}
const sourceFile = getSourceFileOfNode(node);
getOrCreateEmitNode(sourceFile).annotatedNodes.push(node);
}
node.emitNode = {};
}
return node.emitNode;
}
/**
* Gets flags that control emit behavior of a node.
*
* @param node The node.
*/
export function getEmitFlags(node: Node) {
const emitNode = node.emitNode;
return emitNode && emitNode.flags;
}
/**
* Sets flags that control emit behavior of a node.
*
* @param node The node.
* @param emitFlags The NodeEmitFlags for the node.
*/
export function setEmitFlags<T extends Node>(node: T, emitFlags: EmitFlags) {
getOrCreateEmitNode(node).flags = emitFlags;
return node;
}
/**
* Sets a custom text range to use when emitting source maps.
*
* @param node The node.
* @param range The text range.
*/
export function setSourceMapRange<T extends Node>(node: T, range: TextRange) {
getOrCreateEmitNode(node).sourceMapRange = range;
return node;
}
/**
* Sets the TextRange to use for source maps for a token of a node.
*
* @param node The node.
* @param token The token.
* @param range The text range.
*/
export function setTokenSourceMapRange<T extends Node>(node: T, token: SyntaxKind, range: TextRange) {
const emitNode = getOrCreateEmitNode(node);
const tokenSourceMapRanges = emitNode.tokenSourceMapRanges || (emitNode.tokenSourceMapRanges = createMap<TextRange>());
tokenSourceMapRanges[token] = range;
return node;
}
/**
* Sets a custom text range to use when emitting comments.
*/
export function setCommentRange<T extends Node>(node: T, range: TextRange) {
getOrCreateEmitNode(node).commentRange = range;
return node;
}
/**
* Gets a custom text range to use when emitting comments.
*
* @param node The node.
*/
export function getCommentRange(node: Node) {
const emitNode = node.emitNode;
return (emitNode && emitNode.commentRange) || node;
}
/**
* Gets a custom text range to use when emitting source maps.
*
* @param node The node.
*/
export function getSourceMapRange(node: Node) {
const emitNode = node.emitNode;
return (emitNode && emitNode.sourceMapRange) || node;
}
/**
* Gets the TextRange to use for source maps for a token of a node.
*
* @param node The node.
* @param token The token.
*/
export function getTokenSourceMapRange(node: Node, token: SyntaxKind) {
const emitNode = node.emitNode;
const tokenSourceMapRanges = emitNode && emitNode.tokenSourceMapRanges;
return tokenSourceMapRanges && tokenSourceMapRanges[token];
}
/**
* Gets the constant value to emit for an expression.
*/
export function getConstantValue(node: PropertyAccessExpression | ElementAccessExpression) {
const emitNode = node.emitNode;
return emitNode && emitNode.constantValue;
}
/**
* Sets the constant value to emit for an expression.
*/
export function setConstantValue(node: PropertyAccessExpression | ElementAccessExpression, value: number) {
const emitNode = getOrCreateEmitNode(node);
emitNode.constantValue = value;
return node;
}
export function setTextRange<T extends TextRange>(node: T, location: TextRange): T {
if (location) {
node.pos = location.pos;
@@ -2692,7 +2856,7 @@ namespace ts {
return undefined;
}
/**
/**
* Get the name of a target module from an import/export declaration as should be written in the emitted output.
* The emitted output name can be different from the input if:
* 1. The module has a /// <amd-module name="<new name>" />
+91 -455
View File
@@ -18,11 +18,6 @@ namespace ts {
*/
reset(): void;
/**
* Gets test data for source maps.
*/
getSourceMapData(): SourceMapData;
/**
* Set the current source file.
*
@@ -41,123 +36,23 @@ namespace ts {
emitPos(pos: number): void;
/**
* Emits a mapping for the start of a range.
* Emits a node with possible leading and trailing source maps.
*
* If the range's start position is synthetic (undefined or a negative value), no mapping
* will be created. Any trivia at the start position in the original source will be
* skipped.
*
* @param range The range to emit.
* @param emitContext The current emit context
* @param node The node to emit.
* @param emitCallback The callback used to emit the node.
*/
emitStart(range: TextRange): void;
emitNodeWithSourceMap(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void): void;
/**
* Emits a mapping for the start of a range.
*
* If the node's start position is synthetic (undefined or a negative value), no mapping
* will be created. Any trivia at the start position in the original source will be
* skipped.
*
* @param range The range to emit.
* @param contextNode The node for the current range.
* @param ignoreNodeCallback A callback used to determine whether to skip source map
* emit for the start position of this node.
* @param ignoreChildrenCallback A callback used to determine whether to skip source
* map emit for all children of this node.
* @param getTextRangeCallbackCallback A callback used to get a custom source map
* range for this node.
*/
emitStart(range: TextRange, contextNode: Node, ignoreNodeCallback: (node: Node) => boolean, ignoreChildrenCallback: (node: Node) => boolean, getTextRangeCallbackCallback: (node: Node) => TextRange): void;
/**
* Emits a mapping for the end of a range.
*
* If the range's end position is synthetic (undefined or a negative value), no mapping
* will be created.
*
* @param range The range to emit.
*/
emitEnd(range: TextRange): void;
/**
* Emits a mapping for the end of a range.
*
* If the node's end position is synthetic (undefined or a negative value), no mapping
* will be created.
*
* @param range The range to emit.
* @param contextNode The node for the current range.
* @param ignoreNodeCallback A callback used to determine whether to skip source map
* emit for the end position of this node.
* @param ignoreChildrenCallback A callback used to determine whether to skip source
* map emit for all children of this node.
* @param getTextRangeCallbackCallback A callback used to get a custom source map
* range for this node.
*/
emitEnd(range: TextRange, contextNode: Node, ignoreNodeCallback: (node: Node) => boolean, ignoreChildrenCallback: (node: Node) => boolean, getTextRangeCallbackCallback: (node: Node) => TextRange): void;
/**
* Emits a mapping for the start position of a token.
*
* If the token's start position is synthetic (undefined or a negative value), no mapping
* will be created. Any trivia at the start position in the original source will be
* skipped.
* Emits a token of a node node with possible leading and trailing source maps.
*
* @param node The node containing the token.
* @param token The token to emit.
* @param tokenStartPos The start position of the token.
* @returns The start position of the token, following any trivia.
* @param tokenStartPos The start pos of the token.
* @param emitCallback The callback used to emit the token.
*/
emitTokenStart(token: SyntaxKind, tokenStartPos: number): number;
/**
* Emits a mapping for the start position of a token.
*
* If the token's start position is synthetic (undefined or a negative value), no mapping
* will be created. Any trivia at the start position in the original source will be
* skipped.
*
* @param token The token to emit.
* @param tokenStartPos The start position of the token.
* @param contextNode The node containing this token.
* @param ignoreTokenCallback A callback used to determine whether to skip source map
* emit for the start position of this token.
* @param getTokenTextRangeCallback A callback used to get a custom source
* map range for this node.
* @returns The start position of the token, following any trivia.
*/
emitTokenStart(token: SyntaxKind, tokenStartPos: number, contextNode: Node, ignoreTokenCallback: (node: Node, token: SyntaxKind) => boolean, getTokenTextRangeCallback: (node: Node, token: SyntaxKind) => TextRange): number;
/**
* Emits a mapping for the end position of a token.
*
* If the token's end position is synthetic (undefined or a negative value), no mapping
* will be created.
*
* @param token The token to emit.
* @param tokenEndPos The end position of the token.
* @returns The end position of the token.
*/
emitTokenEnd(token: SyntaxKind, tokenEndPos: number): number;
/**
* Emits a mapping for the end position of a token.
*
* If the token's end position is synthetic (undefined or a negative value), no mapping
* will be created.
*
* @param token The token to emit.
* @param tokenEndPos The end position of the token.
* @param contextNode The node containing this token.
* @param ignoreTokenCallback A callback used to determine whether to skip source map
* emit for the end position of this token.
* @param getTokenTextRangeCallback A callback used to get a custom source
* map range for this node.
* @returns The end position of the token.
*/
emitTokenEnd(token: SyntaxKind, tokenEndPos: number, contextNode: Node, ignoreTokenCallback: (node: Node, token: SyntaxKind) => boolean, getTokenTextRangeCallback: (node: Node, token: SyntaxKind) => TextRange): number;
/*@deprecated*/ changeEmitSourcePos(): void;
/*@deprecated*/ stopOverridingSpan(): void;
emitTokenWithSourceMap(node: Node, token: SyntaxKind, tokenStartPos: number, emitCallback: (token: SyntaxKind, tokenStartPos: number) => number): number;
/**
* Gets the text for the source map.
@@ -168,44 +63,11 @@ namespace ts {
* Gets the SourceMappingURL for the source map.
*/
getSourceMappingURL(): string;
}
export function createSourceMapWriter(host: EmitHost, writer: EmitTextWriter): SourceMapWriter {
const compilerOptions = host.getCompilerOptions();
if (compilerOptions.sourceMap || compilerOptions.inlineSourceMap) {
if (compilerOptions.extendedDiagnostics) {
return createSourceMapWriterWithExtendedDiagnostics(host, writer);
}
return createSourceMapWriterWorker(host, writer);
}
else {
return getNullSourceMapWriter();
}
}
let nullSourceMapWriter: SourceMapWriter;
export function getNullSourceMapWriter(): SourceMapWriter {
if (nullSourceMapWriter === undefined) {
nullSourceMapWriter = {
initialize(filePath: string, sourceMapFilePath: string, sourceFiles: SourceFile[], isBundledEmit: boolean): void { },
reset(): void { },
getSourceMapData(): SourceMapData { return undefined; },
setSourceFile(sourceFile: SourceFile): void { },
emitPos(pos: number): void { },
emitStart(range: TextRange, contextNode?: Node, ignoreNodeCallback?: (node: Node) => boolean, ignoreChildrenCallback?: (node: Node) => boolean, getTextRangeCallback?: (node: Node) => TextRange): void { },
emitEnd(range: TextRange, contextNode?: Node, ignoreNodeCallback?: (node: Node) => boolean, ignoreChildrenCallback?: (node: Node) => boolean, getTextRangeCallback?: (node: Node) => TextRange): void { },
emitTokenStart(token: SyntaxKind, pos: number, contextNode?: Node, ignoreTokenCallback?: (node: Node) => boolean, getTokenTextRangeCallback?: (node: Node, token: SyntaxKind) => TextRange): number { return -1; },
emitTokenEnd(token: SyntaxKind, end: number, contextNode?: Node, ignoreTokenCallback?: (node: Node) => boolean, getTokenTextRangeCallback?: (node: Node, token: SyntaxKind) => TextRange): number { return -1; },
changeEmitSourcePos(): void { },
stopOverridingSpan(): void { },
getText(): string { return undefined; },
getSourceMappingURL(): string { return undefined; }
};
}
return nullSourceMapWriter;
/**
* Gets test data for source maps.
*/
getSourceMapData(): SourceMapData;
}
// Used for initialize lastEncodedSourceMapSpan and reset lastEncodedSourceMapSpan when updateLastEncodedAndRecordedSpans
@@ -217,14 +79,12 @@ namespace ts {
sourceIndex: 0
};
function createSourceMapWriterWorker(host: EmitHost, writer: EmitTextWriter): SourceMapWriter {
export function createSourceMapWriter(host: EmitHost, writer: EmitTextWriter): SourceMapWriter {
const compilerOptions = host.getCompilerOptions();
const extendedDiagnostics = compilerOptions.extendedDiagnostics;
let currentSourceFile: SourceFile;
let currentSourceText: string;
let sourceMapDir: string; // The directory in which sourcemap will be
let stopOverridingSpan = false;
let modifyLastSourcePos = false;
// Current source map file and its index in the sources list
let sourceMapSourceIndex: number;
@@ -236,13 +96,7 @@ namespace ts {
// Source map data
let sourceMapData: SourceMapData;
// This keeps track of the number of times `disable` has been called without a
// corresponding call to `enable`. As long as this value is non-zero, mappings will not
// be recorded.
// This is primarily used to provide a better experience when debugging binding
// patterns and destructuring assignments for simple expressions.
let disableDepth: number;
let disabled: boolean = !(compilerOptions.sourceMap || compilerOptions.inlineSourceMap);
return {
initialize,
@@ -250,12 +104,8 @@ namespace ts {
getSourceMapData: () => sourceMapData,
setSourceFile,
emitPos,
emitStart,
emitEnd,
emitTokenStart,
emitTokenEnd,
changeEmitSourcePos,
stopOverridingSpan: () => stopOverridingSpan = true,
emitNodeWithSourceMap,
emitTokenWithSourceMap,
getText,
getSourceMappingURL,
};
@@ -269,13 +119,16 @@ namespace ts {
* @param isBundledEmit A value indicating whether the generated output file is a bundle.
*/
function initialize(filePath: string, sourceMapFilePath: string, sourceFiles: SourceFile[], isBundledEmit: boolean) {
if (disabled) {
return;
}
if (sourceMapData) {
reset();
}
currentSourceFile = undefined;
currentSourceText = undefined;
disableDepth = 0;
// Current source map file and its index in the sources list
sourceMapSourceIndex = -1;
@@ -338,6 +191,10 @@ namespace ts {
* Reset the SourceMapWriter to an empty state.
*/
function reset() {
if (disabled) {
return;
}
currentSourceFile = undefined;
sourceMapDir = undefined;
sourceMapSourceIndex = undefined;
@@ -345,64 +202,6 @@ namespace ts {
lastEncodedSourceMapSpan = undefined;
lastEncodedNameIndex = undefined;
sourceMapData = undefined;
disableDepth = 0;
}
/**
* Re-enables the recording of mappings.
*/
function enable() {
if (disableDepth > 0) {
disableDepth--;
}
}
/**
* Disables the recording of mappings.
*/
function disable() {
disableDepth++;
}
function updateLastEncodedAndRecordedSpans() {
if (modifyLastSourcePos) {
// Reset the source pos
modifyLastSourcePos = false;
// Change Last recorded Map with last encoded emit line and character
lastRecordedSourceMapSpan.emittedLine = lastEncodedSourceMapSpan.emittedLine;
lastRecordedSourceMapSpan.emittedColumn = lastEncodedSourceMapSpan.emittedColumn;
// Pop sourceMapDecodedMappings to remove last entry
sourceMapData.sourceMapDecodedMappings.pop();
// Point the lastEncodedSourceMapSpace to the previous encoded sourceMapSpan
// If the list is empty which indicates that we are at the beginning of the file,
// we have to reset it to default value (same value when we first initialize sourceMapWriter)
lastEncodedSourceMapSpan = sourceMapData.sourceMapDecodedMappings.length ?
sourceMapData.sourceMapDecodedMappings[sourceMapData.sourceMapDecodedMappings.length - 1] :
defaultLastEncodedSourceMapSpan;
// TODO: Update lastEncodedNameIndex
// Since we dont support this any more, lets not worry about it right now.
// When we start supporting nameIndex, we will get back to this
// Change the encoded source map
const sourceMapMappings = sourceMapData.sourceMapMappings;
let lenthToSet = sourceMapMappings.length - 1;
for (; lenthToSet >= 0; lenthToSet--) {
const currentChar = sourceMapMappings.charAt(lenthToSet);
if (currentChar === ",") {
// Separator for the entry found
break;
}
if (currentChar === ";" && lenthToSet !== 0 && sourceMapMappings.charAt(lenthToSet - 1) !== ";") {
// Last line separator found
break;
}
}
sourceMapData.sourceMapMappings = sourceMapMappings.substr(0, Math.max(0, lenthToSet));
}
}
// Encoding for sourcemap span
@@ -459,7 +258,7 @@ namespace ts {
* @param pos The position.
*/
function emitPos(pos: number) {
if (positionIsSynthesized(pos) || disableDepth > 0) {
if (disabled || positionIsSynthesized(pos)) {
return;
}
@@ -495,209 +294,89 @@ namespace ts {
sourceColumn: sourceLinePos.character,
sourceIndex: sourceMapSourceIndex
};
stopOverridingSpan = false;
}
else if (!stopOverridingSpan) {
else {
// Take the new pos instead since there is no change in emittedLine and column since last location
lastRecordedSourceMapSpan.sourceLine = sourceLinePos.line;
lastRecordedSourceMapSpan.sourceColumn = sourceLinePos.character;
lastRecordedSourceMapSpan.sourceIndex = sourceMapSourceIndex;
}
updateLastEncodedAndRecordedSpans();
if (extendedDiagnostics) {
performance.mark("afterSourcemap");
performance.measure("Source Map", "beforeSourcemap", "afterSourcemap");
}
}
function getStartPosPastDecorators(range: TextRange) {
const rangeHasDecorators = !!(range as Node).decorators;
return skipTrivia(currentSourceText, rangeHasDecorators ? (range as Node).decorators.end : range.pos);
}
/**
* Emits a mapping for the start of a range.
* Emits a node with possible leading and trailing source maps.
*
* If the range's start position is synthetic (undefined or a negative value), no mapping
* will be created. Any trivia at the start position in the original source will be
* skipped.
*
* @param range The range to emit.0
* @param node The node to emit.
* @param emitCallback The callback used to emit the node.
*/
function emitStart(range: TextRange): void;
/**
* Emits a mapping for the start of a range.
*
* If the node's start position is synthetic (undefined or a negative value), no mapping
* will be created. Any trivia at the start position in the original source will be
* skipped.
*
* @param range The range to emit.
* @param contextNode The node for the current range.
* @param ignoreNodeCallback A callback used to determine whether to skip source map
* emit for the start position of this node.
* @param ignoreChildrenCallback A callback used to determine whether to skip source
* map emit for all children of this node.
* @param getTextRangeCallbackCallback A callback used to get a custom source map
* range for this node.
*/
function emitStart(range: TextRange, contextNode: Node, ignoreNodeCallback: (node: Node) => boolean, ignoreChildrenCallback: (node: Node) => boolean, getTextRangeCallback: (node: Node) => TextRange): void;
function emitStart(range: TextRange, contextNode?: Node, ignoreNodeCallback?: (node: Node) => boolean, ignoreChildrenCallback?: (node: Node) => boolean, getTextRangeCallback?: (node: Node) => TextRange) {
if (contextNode) {
if (!ignoreNodeCallback(contextNode)) {
range = getTextRangeCallback(contextNode) || range;
emitPos(getStartPosPastDecorators(range));
}
if (ignoreChildrenCallback(contextNode)) {
disable();
}
function emitNodeWithSourceMap(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void) {
if (disabled) {
return emitCallback(emitContext, node);
}
else {
emitPos(getStartPosPastDecorators(range));
if (node) {
const emitNode = node.emitNode;
const emitFlags = emitNode && emitNode.flags;
const { pos, end } = emitNode && emitNode.sourceMapRange || node;
if (node.kind !== SyntaxKind.NotEmittedStatement
&& (emitFlags & EmitFlags.NoLeadingSourceMap) === 0
&& pos >= 0) {
emitPos(skipTrivia(currentSourceText, pos));
}
if (emitFlags & EmitFlags.NoNestedSourceMaps) {
disabled = true;
emitCallback(emitContext, node);
disabled = false;
}
else {
emitCallback(emitContext, node);
}
if (node.kind !== SyntaxKind.NotEmittedStatement
&& (emitFlags & EmitFlags.NoTrailingSourceMap) === 0
&& end >= 0) {
emitPos(end);
}
}
}
/**
* Emits a mapping for the end of a range.
*
* If the range's end position is synthetic (undefined or a negative value), no mapping
* will be created.
*
* @param range The range to emit.
*/
function emitEnd(range: TextRange): void;
/**
* Emits a mapping for the end of a range.
*
* If the node's end position is synthetic (undefined or a negative value), no mapping
* will be created.
*
* @param range The range to emit.
* @param contextNode The node for the current range.
* @param ignoreNodeCallback A callback used to determine whether to skip source map
* emit for the end position of this node.
* @param ignoreChildrenCallback A callback used to determine whether to skip source
* map emit for all children of this node.
* @param getTextRangeCallbackCallback A callback used to get a custom source map
* range for this node.
*/
function emitEnd(range: TextRange, contextNode: Node, ignoreNodeCallback: (node: Node) => boolean, ignoreChildrenCallback: (node: Node) => boolean, getTextRangeCallback: (node: Node) => TextRange): void;
function emitEnd(range: TextRange, contextNode?: Node, ignoreNodeCallback?: (node: Node) => boolean, ignoreChildrenCallback?: (node: Node) => boolean, getTextRangeCallback?: (node: Node) => TextRange) {
if (contextNode) {
if (ignoreChildrenCallback(contextNode)) {
enable();
}
if (!ignoreNodeCallback(contextNode)) {
range = getTextRangeCallback(contextNode) || range;
emitPos(range.end);
}
}
else {
emitPos(range.end);
}
stopOverridingSpan = false;
}
/**
* Emits a mapping for the start position of a token.
*
* If the token's start position is synthetic (undefined or a negative value), no mapping
* will be created. Any trivia at the start position in the original source will be
* skipped.
* Emits a token of a node with possible leading and trailing source maps.
*
* @param node The node containing the token.
* @param token The token to emit.
* @param tokenStartPos The start position of the token.
* @returns The start position of the token, following any trivia.
* @param tokenStartPos The start pos of the token.
* @param emitCallback The callback used to emit the token.
*/
function emitTokenStart(token: SyntaxKind, tokenStartPos: number): number;
/**
* Emits a mapping for the start position of a token.
*
* If the token's start position is synthetic (undefined or a negative value), no mapping
* will be created. Any trivia at the start position in the original source will be
* skipped.
*
* @param token The token to emit.
* @param tokenStartPos The start position of the token.
* @param contextNode The node containing this token.
* @param ignoreTokenCallback A callback used to determine whether to skip source map
* emit for the start position of this token.
* @param getTokenTextRangeCallback A callback used to get a custom source
* map range for this node.
* @returns The start position of the token, following any trivia.
*/
function emitTokenStart(token: SyntaxKind, tokenStartPos: number, contextNode: Node, ignoreTokenCallback: (node: Node, token: SyntaxKind) => boolean, getTokenTextRangeCallback: (node: Node, token: SyntaxKind) => TextRange): number;
function emitTokenStart(token: SyntaxKind, tokenStartPos: number, contextNode?: Node, ignoreTokenCallback?: (node: Node, token: SyntaxKind) => boolean, getTokenTextRangeCallback?: (node: Node, token: SyntaxKind) => TextRange): number {
if (contextNode) {
if (ignoreTokenCallback(contextNode, token)) {
return skipTrivia(currentSourceText, tokenStartPos);
}
const range = getTokenTextRangeCallback(contextNode, token);
if (range) {
tokenStartPos = range.pos;
}
function emitTokenWithSourceMap(node: Node, token: SyntaxKind, tokenPos: number, emitCallback: (token: SyntaxKind, tokenStartPos: number) => number) {
if (disabled) {
return emitCallback(token, tokenPos);
}
tokenStartPos = skipTrivia(currentSourceText, tokenStartPos);
emitPos(tokenStartPos);
return tokenStartPos;
}
const emitNode = node && node.emitNode;
const emitFlags = emitNode && emitNode.flags;
const range = emitNode && emitNode.tokenSourceMapRanges && emitNode.tokenSourceMapRanges[token];
/**
* Emits a mapping for the end position of a token.
*
* If the token's end position is synthetic (undefined or a negative value), no mapping
* will be created.
*
* @param token The token to emit.
* @param tokenEndPos The end position of the token.
* @returns The end position of the token.
*/
function emitTokenEnd(token: SyntaxKind, tokenEndPos: number): number;
/**
* Emits a mapping for the end position of a token.
*
* If the token's end position is synthetic (undefined or a negative value), no mapping
* will be created.
*
* @param token The token to emit.
* @param tokenEndPos The end position of the token.
* @param contextNode The node containing this token.
* @param ignoreTokenCallback A callback used to determine whether to skip source map
* emit for the end position of this token.
* @param getTokenTextRangeCallback A callback used to get a custom source
* map range for this node.
* @returns The end position of the token.
*/
function emitTokenEnd(token: SyntaxKind, tokenEndPos: number, contextNode: Node, ignoreTokenCallback: (node: Node, token: SyntaxKind) => boolean, getTokenTextRangeCallback: (node: Node, token: SyntaxKind) => TextRange): number;
function emitTokenEnd(token: SyntaxKind, tokenEndPos: number, contextNode?: Node, ignoreTokenCallback?: (node: Node, token: SyntaxKind) => boolean, getTokenTextRangeCallback?: (node: Node, token: SyntaxKind) => TextRange): number {
if (contextNode) {
if (ignoreTokenCallback(contextNode, token)) {
return tokenEndPos;
}
const range = getTokenTextRangeCallback(contextNode, token);
if (range) {
tokenEndPos = range.end;
}
tokenPos = skipTrivia(currentSourceText, range ? range.pos : tokenPos);
if ((emitFlags & EmitFlags.NoTokenLeadingSourceMaps) === 0 && tokenPos >= 0) {
emitPos(tokenPos);
}
emitPos(tokenEndPos);
return tokenEndPos;
}
tokenPos = emitCallback(token, tokenPos);
if (range) tokenPos = range.end;
if ((emitFlags & EmitFlags.NoTokenTrailingSourceMaps) === 0 && tokenPos >= 0) {
emitPos(tokenPos);
}
// @deprecated
function changeEmitSourcePos() {
Debug.assert(!modifyLastSourcePos);
modifyLastSourcePos = true;
return tokenPos;
}
/**
@@ -706,6 +385,10 @@ namespace ts {
* @param sourceFile The source file.
*/
function setSourceFile(sourceFile: SourceFile) {
if (disabled) {
return;
}
currentSourceFile = sourceFile;
currentSourceText = currentSourceFile.text;
@@ -738,6 +421,10 @@ namespace ts {
* Gets the text for the source map.
*/
function getText() {
if (disabled) {
return;
}
encodeLastRecordedSourceMapSpan();
return stringify({
@@ -755,6 +442,10 @@ namespace ts {
* Gets the SourceMappingURL for the source map.
*/
function getSourceMappingURL() {
if (disabled) {
return;
}
if (compilerOptions.inlineSourceMap) {
// Encode the sourceMap into the sourceMap url
const base64SourceMapText = convertToBase64(getText());
@@ -766,61 +457,6 @@ namespace ts {
}
}
function createSourceMapWriterWithExtendedDiagnostics(host: EmitHost, writer: EmitTextWriter): SourceMapWriter {
const {
initialize,
reset,
getSourceMapData,
setSourceFile,
emitPos,
emitStart,
emitEnd,
emitTokenStart,
emitTokenEnd,
changeEmitSourcePos,
stopOverridingSpan,
getText,
getSourceMappingURL,
} = createSourceMapWriterWorker(host, writer);
return {
initialize,
reset,
getSourceMapData,
setSourceFile,
emitPos(pos: number): void {
performance.mark("sourcemapStart");
emitPos(pos);
performance.measure("sourceMapTime", "sourcemapStart");
},
emitStart(range: TextRange, contextNode?: Node, ignoreNodeCallback?: (node: Node) => boolean, ignoreChildrenCallback?: (node: Node) => boolean, getTextRangeCallback?: (node: Node) => TextRange): void {
performance.mark("emitSourcemap:emitStart");
emitStart(range, contextNode, ignoreNodeCallback, ignoreChildrenCallback, getTextRangeCallback);
performance.measure("sourceMapTime", "emitSourcemap:emitStart");
},
emitEnd(range: TextRange, contextNode?: Node, ignoreNodeCallback?: (node: Node) => boolean, ignoreChildrenCallback?: (node: Node) => boolean, getTextRangeCallback?: (node: Node) => TextRange): void {
performance.mark("emitSourcemap:emitEnd");
emitEnd(range, contextNode, ignoreNodeCallback, ignoreChildrenCallback, getTextRangeCallback);
performance.measure("sourceMapTime", "emitSourcemap:emitEnd");
},
emitTokenStart(token: SyntaxKind, tokenStartPos: number, contextNode?: Node, ignoreTokenCallback?: (node: Node) => boolean, getTokenTextRangeCallback?: (node: Node, token: SyntaxKind) => TextRange): number {
performance.mark("emitSourcemap:emitTokenStart");
tokenStartPos = emitTokenStart(token, tokenStartPos, contextNode, ignoreTokenCallback, getTokenTextRangeCallback);
performance.measure("sourceMapTime", "emitSourcemap:emitTokenStart");
return tokenStartPos;
},
emitTokenEnd(token: SyntaxKind, tokenEndPos: number, contextNode?: Node, ignoreTokenCallback?: (node: Node) => boolean, getTokenTextRangeCallback?: (node: Node, token: SyntaxKind) => TextRange): number {
performance.mark("emitSourcemap:emitTokenEnd");
tokenEndPos = emitTokenEnd(token, tokenEndPos, contextNode, ignoreTokenCallback, getTokenTextRangeCallback);
performance.measure("sourceMapTime", "emitSourcemap:emitTokenEnd");
return tokenEndPos;
},
changeEmitSourcePos,
stopOverridingSpan,
getText,
getSourceMappingURL,
};
}
const base64Chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
function base64FormatEncode(inValue: number) {
+44 -334
View File
@@ -28,46 +28,25 @@ namespace ts {
/**
* Gets the transformed source files.
*/
getSourceFiles(): SourceFile[];
transformed: SourceFile[];
/**
* Gets the TextRange to use for source maps for a token of a node.
*/
getTokenSourceMapRange(node: Node, token: SyntaxKind): TextRange;
/**
* Determines whether expression substitutions are enabled for the provided node.
*/
isSubstitutionEnabled(node: Node): boolean;
/**
* Determines whether before/after emit notifications should be raised in the pretty
* printer when it emits a node.
*/
isEmitNotificationEnabled(node: Node): boolean;
/**
* Hook used by transformers to substitute expressions just before they
* are emitted by the pretty printer.
* Emits the substitute for a node, if one is available; otherwise, emits the node.
*
* @param emitContext The current emit context.
* @param node The node to substitute.
* @param isExpression A value indicating whether the node is in an expression context.
* @param emitCallback A callback used to emit the node or its substitute.
*/
onSubstituteNode(node: Node, isExpression: boolean): Node;
emitNodeWithSubstitution(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void): void;
/**
* Hook used to allow transformers to capture state before or after
* the printer emits a node.
* Emits a node with possible notification.
*
* @param emitContext The current emit context.
* @param node The node to emit.
* @param emitCallback A callback used to emit the node.
*/
onEmitNode(node: Node, emitCallback: (node: Node) => void): void;
/**
* Reset transient transformation properties on parse tree nodes.
*/
dispose(): void;
emitNodeWithNotification(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void): void;
}
export interface TransformationContext extends LexicalEnvironment {
@@ -75,46 +54,6 @@ namespace ts {
getEmitResolver(): EmitResolver;
getEmitHost(): EmitHost;
/**
* Gets flags used to customize later transformations or emit.
*/
getNodeEmitFlags(node: Node): NodeEmitFlags;
/**
* Sets flags used to customize later transformations or emit.
*/
setNodeEmitFlags<T extends Node>(node: T, flags: NodeEmitFlags): T;
/**
* Gets the TextRange to use for source maps for the node.
*/
getSourceMapRange(node: Node): TextRange;
/**
* Sets the TextRange to use for source maps for the node.
*/
setSourceMapRange<T extends Node>(node: T, range: TextRange): T;
/**
* Gets the TextRange to use for source maps for a token of a node.
*/
getTokenSourceMapRange(node: Node, token: SyntaxKind): TextRange;
/**
* Sets the TextRange to use for source maps for a token of a node.
*/
setTokenSourceMapRange<T extends Node>(node: T, token: SyntaxKind, range: TextRange): T;
/**
* Gets the TextRange to use for comments for the node.
*/
getCommentRange(node: Node): TextRange;
/**
* Sets the TextRange to use for comments for the node.
*/
setCommentRange<T extends Node>(node: T, range: TextRange): T;
/**
* Hoists a function declaration to the containing scope.
*/
@@ -139,7 +78,7 @@ namespace ts {
* Hook used by transformers to substitute expressions just before they
* are emitted by the pretty printer.
*/
onSubstituteNode?: (node: Node, isExpression: boolean) => Node;
onSubstituteNode?: (emitContext: EmitContext, node: Node) => Node;
/**
* Enables before/after emit notifications in the pretty printer for the provided
@@ -157,7 +96,7 @@ namespace ts {
* Hook used to allow transformers to capture state before or after
* the printer emits a node.
*/
onEmitNode?: (node: Node, emit: (node: Node) => void) => void;
onEmitNode?: (emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void) => void;
}
/* @internal */
@@ -186,14 +125,6 @@ namespace ts {
return transformers;
}
/**
* Tracks a monotonically increasing transformation id used to associate a node with a specific
* transformation. This ensures transient properties related to transformations can be safely
* stored on source tree nodes that may be reused across multiple transformations (such as
* with compile-on-save).
*/
let nextTransformId = 1;
/**
* Transforms an array of SourceFiles by passing them through each transformer.
*
@@ -203,18 +134,10 @@ namespace ts {
* @param transforms An array of Transformers.
*/
export function transformFiles(resolver: EmitResolver, host: EmitHost, sourceFiles: SourceFile[], transformers: Transformer[]): TransformationResult {
const transformId = nextTransformId;
nextTransformId++;
const tokenSourceMapRanges = createMap<TextRange>();
const lexicalEnvironmentVariableDeclarationsStack: VariableDeclaration[][] = [];
const lexicalEnvironmentFunctionDeclarationsStack: FunctionDeclaration[][] = [];
const enabledSyntaxKindFeatures = new Array<SyntaxKindFeatureFlags>(SyntaxKind.Count);
const parseTreeNodesWithAnnotations: Node[] = [];
let lastTokenSourceMapRangeNode: Node;
let lastTokenSourceMapRangeToken: SyntaxKind;
let lastTokenSourceMapRange: TextRange;
let lexicalEnvironmentStackOffset = 0;
let hoistedVariableDeclarations: VariableDeclaration[];
let hoistedFunctionDeclarations: FunctionDeclaration[];
@@ -226,22 +149,14 @@ namespace ts {
getCompilerOptions: () => host.getCompilerOptions(),
getEmitResolver: () => resolver,
getEmitHost: () => host,
getNodeEmitFlags,
setNodeEmitFlags,
getSourceMapRange,
setSourceMapRange,
getTokenSourceMapRange,
setTokenSourceMapRange,
getCommentRange,
setCommentRange,
hoistVariableDeclaration,
hoistFunctionDeclaration,
startLexicalEnvironment,
endLexicalEnvironment,
onSubstituteNode,
onSubstituteNode: (emitContext, node) => node,
enableSubstitution,
isSubstitutionEnabled,
onEmitNode,
onEmitNode: (node, emitContext, emitCallback) => emitCallback(node, emitContext),
enableEmitNotification,
isEmitNotificationEnabled
};
@@ -256,30 +171,9 @@ namespace ts {
lexicalEnvironmentDisabled = true;
return {
getSourceFiles: () => transformed,
getTokenSourceMapRange,
isSubstitutionEnabled,
isEmitNotificationEnabled,
onSubstituteNode: context.onSubstituteNode,
onEmitNode: context.onEmitNode,
dispose() {
// During transformation we may need to annotate a parse tree node with transient
// transformation properties. As parse tree nodes live longer than transformation
// nodes, we need to make sure we reclaim any memory allocated for custom ranges
// from these nodes to ensure we do not hold onto entire subtrees just for position
// information. We also need to reset these nodes to a pre-transformation state
// for incremental parsing scenarios so that we do not impact later emit.
for (const node of parseTreeNodesWithAnnotations) {
if (node.transformId === transformId) {
node.transformId = 0;
node.emitFlags = 0;
node.commentRange = undefined;
node.sourceMapRange = undefined;
}
}
parseTreeNodesWithAnnotations.length = 0;
}
transformed,
emitNodeWithSubstitution,
emitNodeWithNotification
};
/**
@@ -306,18 +200,29 @@ namespace ts {
* Determines whether expression substitutions are enabled for the provided node.
*/
function isSubstitutionEnabled(node: Node) {
return (enabledSyntaxKindFeatures[node.kind] & SyntaxKindFeatureFlags.Substitution) !== 0;
return (enabledSyntaxKindFeatures[node.kind] & SyntaxKindFeatureFlags.Substitution) !== 0
&& (getEmitFlags(node) & EmitFlags.NoSubstitution) === 0;
}
/**
* Default hook for node substitutions.
* Emits a node with possible substitution.
*
* @param node The node to substitute.
* @param isExpression A value indicating whether the node is to be used in an expression
* position.
* @param emitContext The current emit context.
* @param node The node to emit.
* @param emitCallback The callback used to emit the node or its substitute.
*/
function onSubstituteNode(node: Node, isExpression: boolean) {
return node;
function emitNodeWithSubstitution(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void) {
if (node) {
if (isSubstitutionEnabled(node)) {
const substitute = context.onSubstituteNode(emitContext, node);
if (substitute && substitute !== node) {
emitCallback(emitContext, substitute);
return;
}
}
emitCallback(emitContext, node);
}
}
/**
@@ -333,154 +238,25 @@ namespace ts {
*/
function isEmitNotificationEnabled(node: Node) {
return (enabledSyntaxKindFeatures[node.kind] & SyntaxKindFeatureFlags.EmitNotifications) !== 0
|| (getNodeEmitFlags(node) & NodeEmitFlags.AdviseOnEmitNode) !== 0;
|| (getEmitFlags(node) & EmitFlags.AdviseOnEmitNode) !== 0;
}
/**
* Default hook for node emit.
* Emits a node with possible emit notification.
*
* @param emitContext The current emit context.
* @param node The node to emit.
* @param emit A callback used to emit the node in the printer.
* @param emitCallback The callback used to emit the node.
*/
function onEmitNode(node: Node, emit: (node: Node) => void) {
emit(node);
}
/**
* Associates a node with the current transformation, initializing
* various transient transformation properties.
*
* @param node The node.
*/
function beforeSetAnnotation(node: Node) {
if ((node.flags & NodeFlags.Synthesized) === 0 && node.transformId !== transformId) {
// To avoid holding onto transformation artifacts, we keep track of any
// parse tree node we are annotating. This allows us to clean them up after
// all transformations have completed.
parseTreeNodesWithAnnotations.push(node);
node.transformId = transformId;
}
}
/**
* Gets flags that control emit behavior of a node.
*
* If the node does not have its own NodeEmitFlags set, the node emit flags of its
* original pointer are used.
*
* @param node The node.
*/
function getNodeEmitFlags(node: Node) {
return node.emitFlags;
}
/**
* Sets flags that control emit behavior of a node.
*
* @param node The node.
* @param emitFlags The NodeEmitFlags for the node.
*/
function setNodeEmitFlags<T extends Node>(node: T, emitFlags: NodeEmitFlags) {
beforeSetAnnotation(node);
node.emitFlags = emitFlags;
return node;
}
/**
* Gets a custom text range to use when emitting source maps.
*
* If a node does not have its own custom source map text range, the custom source map
* text range of its original pointer is used.
*
* @param node The node.
*/
function getSourceMapRange(node: Node) {
return node.sourceMapRange || node;
}
/**
* Sets a custom text range to use when emitting source maps.
*
* @param node The node.
* @param range The text range.
*/
function setSourceMapRange<T extends Node>(node: T, range: TextRange) {
beforeSetAnnotation(node);
node.sourceMapRange = range;
return node;
}
/**
* Gets the TextRange to use for source maps for a token of a node.
*
* If a node does not have its own custom source map text range for a token, the custom
* source map text range for the token of its original pointer is used.
*
* @param node The node.
* @param token The token.
*/
function getTokenSourceMapRange(node: Node, token: SyntaxKind) {
// As a performance optimization, use the cached value of the most recent node.
// This helps for cases where this function is called repeatedly for the same node.
if (lastTokenSourceMapRangeNode === node && lastTokenSourceMapRangeToken === token) {
return lastTokenSourceMapRange;
}
// Get the custom token source map range for a node or from one of its original nodes.
// Custom token ranges are not stored on the node to avoid the GC burden.
let range: TextRange;
let current = node;
while (current) {
range = current.id ? tokenSourceMapRanges[current.id + "-" + token] : undefined;
if (range !== undefined) {
break;
function emitNodeWithNotification(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void) {
if (node) {
if (isEmitNotificationEnabled(node)) {
context.onEmitNode(emitContext, node, emitCallback);
}
else {
emitCallback(emitContext, node);
}
current = current.original;
}
// Cache the most recently requested value.
lastTokenSourceMapRangeNode = node;
lastTokenSourceMapRangeToken = token;
lastTokenSourceMapRange = range;
return range;
}
/**
* Sets the TextRange to use for source maps for a token of a node.
*
* @param node The node.
* @param token The token.
* @param range The text range.
*/
function setTokenSourceMapRange<T extends Node>(node: T, token: SyntaxKind, range: TextRange) {
// Cache the most recently requested value.
lastTokenSourceMapRangeNode = node;
lastTokenSourceMapRangeToken = token;
lastTokenSourceMapRange = range;
tokenSourceMapRanges[getNodeId(node) + "-" + token] = range;
return node;
}
/**
* Gets a custom text range to use when emitting comments.
*
* If a node does not have its own custom source map text range, the custom source map
* text range of its original pointer is used.
*
* @param node The node.
*/
function getCommentRange(node: Node) {
return node.commentRange || node;
}
/**
* Sets a custom text range to use when emitting comments.
*/
function setCommentRange<T extends Node>(node: T, range: TextRange) {
beforeSetAnnotation(node);
node.commentRange = range;
return node;
}
/**
@@ -563,70 +339,4 @@ namespace ts {
return statements;
}
}
/**
* High-order function, creates a function that executes a function composition.
* For example, `chain(a, b)` is the equivalent of `x => ((a', b') => y => b'(a'(y)))(a(x), b(x))`
*
* @param args The functions to chain.
*/
function chain<T, U>(...args: ((t: T) => (u: U) => U)[]): (t: T) => (u: U) => U;
function chain<T, U>(a: (t: T) => (u: U) => U, b: (t: T) => (u: U) => U, c: (t: T) => (u: U) => U, d: (t: T) => (u: U) => U, e: (t: T) => (u: U) => U): (t: T) => (u: U) => U {
if (e) {
const args: ((t: T) => (u: U) => U)[] = [];
for (let i = 0; i < arguments.length; i++) {
args[i] = arguments[i];
}
return t => compose(...map(args, f => f(t)));
}
else if (d) {
return t => compose(a(t), b(t), c(t), d(t));
}
else if (c) {
return t => compose(a(t), b(t), c(t));
}
else if (b) {
return t => compose(a(t), b(t));
}
else if (a) {
return t => compose(a(t));
}
else {
return t => u => u;
}
}
/**
* High-order function, composes functions. Note that functions are composed inside-out;
* for example, `compose(a, b)` is the equivalent of `x => b(a(x))`.
*
* @param args The functions to compose.
*/
function compose<T>(...args: ((t: T) => T)[]): (t: T) => T;
function compose<T>(a: (t: T) => T, b: (t: T) => T, c: (t: T) => T, d: (t: T) => T, e: (t: T) => T): (t: T) => T {
if (e) {
const args: ((t: T) => T)[] = [];
for (let i = 0; i < arguments.length; i++) {
args[i] = arguments[i];
}
return t => reduceLeft<(t: T) => T, T>(args, (u, f) => f(u), t);
}
else if (d) {
return t => d(c(b(a(t))));
}
else if (c) {
return t => c(b(a(t)));
}
else if (b) {
return t => b(a(t));
}
else if (a) {
return t => a(t);
}
else {
return t => t;
}
}
}
+6 -6
View File
@@ -66,7 +66,7 @@ namespace ts {
// NOTE: this completely disables source maps, but aligns with the behavior of
// `emitAssignment` in the old emitter.
context.setNodeEmitFlags(expression, NodeEmitFlags.NoNestedSourceMaps);
setEmitFlags(expression, EmitFlags.NoNestedSourceMaps);
aggregateTransformFlags(expression);
expressions.push(expression);
@@ -102,7 +102,7 @@ namespace ts {
// NOTE: this completely disables source maps, but aligns with the behavior of
// `emitAssignment` in the old emitter.
context.setNodeEmitFlags(declaration, NodeEmitFlags.NoNestedSourceMaps);
setEmitFlags(declaration, EmitFlags.NoNestedSourceMaps);
aggregateTransformFlags(declaration);
declarations.push(declaration);
@@ -147,7 +147,7 @@ namespace ts {
// NOTE: this completely disables source maps, but aligns with the behavior of
// `emitAssignment` in the old emitter.
context.setNodeEmitFlags(declaration, NodeEmitFlags.NoNestedSourceMaps);
setEmitFlags(declaration, EmitFlags.NoNestedSourceMaps);
declarations.push(declaration);
aggregateTransformFlags(declaration);
@@ -211,7 +211,7 @@ namespace ts {
// NOTE: this completely disables source maps, but aligns with the behavior of
// `emitAssignment` in the old emitter.
context.setNodeEmitFlags(expression, NodeEmitFlags.NoNestedSourceMaps);
setEmitFlags(expression, EmitFlags.NoNestedSourceMaps);
pendingAssignments.push(expression);
return expression;
@@ -271,8 +271,8 @@ namespace ts {
}
else {
const name = getMutableClone(<Identifier>target);
context.setSourceMapRange(name, target);
context.setCommentRange(name, target);
setSourceMapRange(name, target);
setCommentRange(name, target);
emitAssignment(name, value, location, /*original*/ undefined);
}
}
+294 -117
View File
@@ -139,18 +139,35 @@ namespace ts {
loopOutParameters?: LoopOutParameter[];
}
const enum SuperCaptureResult {
/**
* A capture may have been added for calls to 'super', but
* the caller should emit subsequent statements normally.
*/
NoReplacement,
/**
* A call to 'super()' got replaced with a capturing statement like:
*
* var _this = _super.call(...) || this;
*
* Callers should skip the current statement.
*/
ReplaceSuperCapture,
/**
* A call to 'super()' got replaced with a capturing statement like:
*
* return _super.call(...) || this;
*
* Callers should skip the current statement and avoid any returns of '_this'.
*/
ReplaceWithReturn,
}
export function transformES6(context: TransformationContext) {
const {
startLexicalEnvironment,
endLexicalEnvironment,
hoistVariableDeclaration,
getNodeEmitFlags,
setNodeEmitFlags,
getCommentRange,
setCommentRange,
getSourceMapRange,
setSourceMapRange,
setTokenSourceMapRange,
} = context;
const resolver = context.getEmitResolver();
@@ -185,6 +202,10 @@ namespace ts {
return transformSourceFile;
function transformSourceFile(node: SourceFile) {
if (isDeclarationFile(node)) {
return node;
}
currentSourceFile = node;
currentText = node.text;
return visitNode(node, visitor, isSourceFile);
@@ -200,7 +221,7 @@ namespace ts {
: visitorWorker(node);
}
function saveStateAndInvoke<T>(node: Node, f: (node: Node) => T): T {
function saveStateAndInvoke<T extends Node, U>(node: T, f: (node: T) => U): U {
const savedEnclosingFunction = enclosingFunction;
const savedEnclosingNonArrowFunction = enclosingNonArrowFunction;
const savedEnclosingNonAsyncFunctionBody = enclosingNonAsyncFunctionBody;
@@ -408,7 +429,7 @@ namespace ts {
enclosingFunction = currentNode;
if (currentNode.kind !== SyntaxKind.ArrowFunction) {
enclosingNonArrowFunction = currentNode;
if (!(currentNode.emitFlags & NodeEmitFlags.AsyncFunctionBody)) {
if (!(getEmitFlags(currentNode) & EmitFlags.AsyncFunctionBody)) {
enclosingNonAsyncFunctionBody = currentNode;
}
}
@@ -671,19 +692,19 @@ namespace ts {
// To preserve the behavior of the old emitter, we explicitly indent
// the body of the function here if it was requested in an earlier
// transformation.
if (getNodeEmitFlags(node) & NodeEmitFlags.Indented) {
setNodeEmitFlags(classFunction, NodeEmitFlags.Indented);
if (getEmitFlags(node) & EmitFlags.Indented) {
setEmitFlags(classFunction, EmitFlags.Indented);
}
// "inner" and "outer" below are added purely to preserve source map locations from
// the old emitter
const inner = createPartiallyEmittedExpression(classFunction);
inner.end = node.end;
setNodeEmitFlags(inner, NodeEmitFlags.NoComments);
setEmitFlags(inner, EmitFlags.NoComments);
const outer = createPartiallyEmittedExpression(inner);
outer.end = skipTrivia(currentText, node.pos);
setNodeEmitFlags(outer, NodeEmitFlags.NoComments);
setEmitFlags(outer, EmitFlags.NoComments);
return createParen(
createCall(
@@ -717,17 +738,17 @@ namespace ts {
// emit with the original emitter.
const outer = createPartiallyEmittedExpression(localName);
outer.end = closingBraceLocation.end;
setNodeEmitFlags(outer, NodeEmitFlags.NoComments);
setEmitFlags(outer, EmitFlags.NoComments);
const statement = createReturn(outer);
statement.pos = closingBraceLocation.pos;
setNodeEmitFlags(statement, NodeEmitFlags.NoComments | NodeEmitFlags.NoTokenSourceMaps);
setEmitFlags(statement, EmitFlags.NoComments | EmitFlags.NoTokenSourceMaps);
statements.push(statement);
addRange(statements, endLexicalEnvironment());
const block = createBlock(createNodeArray(statements, /*location*/ node.members), /*location*/ undefined, /*multiLine*/ true);
setNodeEmitFlags(block, NodeEmitFlags.NoComments);
setEmitFlags(block, EmitFlags.NoComments);
return block;
}
@@ -759,7 +780,8 @@ namespace ts {
function addConstructor(statements: Statement[], node: ClassExpression | ClassDeclaration, extendsClauseElement: ExpressionWithTypeArguments): void {
const constructor = getFirstConstructorWithBody(node);
const hasSynthesizedSuper = hasSynthesizedDefaultSuperCall(constructor, extendsClauseElement !== undefined);
statements.push(
const constructorFunction =
createFunctionDeclaration(
/*decorators*/ undefined,
/*modifiers*/ undefined,
@@ -770,8 +792,12 @@ namespace ts {
/*type*/ undefined,
transformConstructorBody(constructor, node, extendsClauseElement, hasSynthesizedSuper),
/*location*/ constructor || node
)
);
);
if (extendsClauseElement) {
setEmitFlags(constructorFunction, EmitFlags.CapturesThis);
}
statements.push(constructorFunction);
}
/**
@@ -803,22 +829,53 @@ namespace ts {
* @param hasSynthesizedSuper A value indicating whether the constructor starts with a
* synthesized `super` call.
*/
function transformConstructorBody(constructor: ConstructorDeclaration, node: ClassDeclaration | ClassExpression, extendsClauseElement: ExpressionWithTypeArguments, hasSynthesizedSuper: boolean) {
function transformConstructorBody(constructor: ConstructorDeclaration | undefined, node: ClassDeclaration | ClassExpression, extendsClauseElement: ExpressionWithTypeArguments, hasSynthesizedSuper: boolean) {
const statements: Statement[] = [];
startLexicalEnvironment();
if (constructor) {
addCaptureThisForNodeIfNeeded(statements, constructor);
addDefaultValueAssignmentsIfNeeded(statements, constructor);
addRestParameterIfNeeded(statements, constructor, hasSynthesizedSuper);
let statementOffset = -1;
if (hasSynthesizedSuper) {
// If a super call has already been synthesized,
// we're going to assume that we should just transform everything after that.
// The assumption is that no prior step in the pipeline has added any prologue directives.
statementOffset = 1;
}
else if (constructor) {
// Otherwise, try to emit all potential prologue directives first.
statementOffset = addPrologueDirectives(statements, constructor.body.statements, /*ensureUseStrict*/ false, visitor);
}
addDefaultSuperCallIfNeeded(statements, constructor, extendsClauseElement, hasSynthesizedSuper);
if (constructor) {
addDefaultValueAssignmentsIfNeeded(statements, constructor);
addRestParameterIfNeeded(statements, constructor, hasSynthesizedSuper);
Debug.assert(statementOffset >= 0, "statementOffset not initialized correctly!");
}
const superCaptureStatus = declareOrCaptureOrReturnThisForConstructorIfNeeded(statements, constructor, !!extendsClauseElement, hasSynthesizedSuper, statementOffset);
// The last statement expression was replaced. Skip it.
if (superCaptureStatus === SuperCaptureResult.ReplaceSuperCapture || superCaptureStatus === SuperCaptureResult.ReplaceWithReturn) {
statementOffset++;
}
if (constructor) {
const body = saveStateAndInvoke(constructor, hasSynthesizedSuper ? transformConstructorBodyWithSynthesizedSuper : transformConstructorBodyWithoutSynthesizedSuper);
const body = saveStateAndInvoke(constructor, constructor => visitNodes(constructor.body.statements, visitor, isStatement, /*start*/ statementOffset));
addRange(statements, body);
}
// Return `_this` unless we're sure enough that it would be pointless to add a return statement.
// If there's a constructor that we can tell returns in enough places, then we *do not* want to add a return.
if (extendsClauseElement
&& superCaptureStatus !== SuperCaptureResult.ReplaceWithReturn
&& !(constructor && isSufficientlyCoveredByReturnStatements(constructor.body))) {
statements.push(
createReturn(
createIdentifier("_this")
)
);
}
addRange(statements, endLexicalEnvironment());
const block = createBlock(
createNodeArray(
@@ -830,47 +887,136 @@ namespace ts {
);
if (!constructor) {
setNodeEmitFlags(block, NodeEmitFlags.NoComments);
setEmitFlags(block, EmitFlags.NoComments);
}
return block;
}
function transformConstructorBodyWithSynthesizedSuper(node: ConstructorDeclaration) {
return visitNodes(node.body.statements, visitor, isStatement, 1);
}
/**
* We want to try to avoid emitting a return statement in certain cases if a user already returned something.
* It would generate obviously dead code, so we'll try to make things a little bit prettier
* by doing a minimal check on whether some common patterns always explicitly return.
*/
function isSufficientlyCoveredByReturnStatements(statement: Statement): boolean {
// A return statement is considered covered.
if (statement.kind === SyntaxKind.ReturnStatement) {
return true;
}
// An if-statement with two covered branches is covered.
else if (statement.kind === SyntaxKind.IfStatement) {
const ifStatement = statement as IfStatement;
if (ifStatement.elseStatement) {
return isSufficientlyCoveredByReturnStatements(ifStatement.thenStatement) &&
isSufficientlyCoveredByReturnStatements(ifStatement.elseStatement);
}
}
// A block is covered if it has a last statement which is covered.
else if (statement.kind === SyntaxKind.Block) {
const lastStatement = lastOrUndefined((statement as Block).statements);
if (lastStatement && isSufficientlyCoveredByReturnStatements(lastStatement)) {
return true;
}
}
function transformConstructorBodyWithoutSynthesizedSuper(node: ConstructorDeclaration) {
return visitNodes(node.body.statements, visitor, isStatement, 0);
return false;
}
/**
* Adds a synthesized call to `_super` if it is needed.
* Declares a `_this` variable for derived classes and for when arrow functions capture `this`.
*
* @param statements The statements for the new constructor body.
* @param constructor The constructor for the class.
* @param extendsClauseElement The expression for the class `extends` clause.
* @param hasSynthesizedSuper A value indicating whether the constructor starts with a
* synthesized `super` call.
* @returns The new statement offset into the `statements` array.
*/
function addDefaultSuperCallIfNeeded(statements: Statement[], constructor: ConstructorDeclaration, extendsClauseElement: ExpressionWithTypeArguments, hasSynthesizedSuper: boolean) {
// If the TypeScript transformer needed to synthesize a constructor for property
// initializers, it would have also added a synthetic `...args` parameter and
// `super` call.
// If this is the case, or if the class has an `extends` clause but no
// constructor, we emit a synthesized call to `_super`.
if (constructor ? hasSynthesizedSuper : extendsClauseElement) {
statements.push(
createStatement(
createFunctionApply(
createIdentifier("_super"),
createThis(),
createIdentifier("arguments")
),
/*location*/ extendsClauseElement
)
);
function declareOrCaptureOrReturnThisForConstructorIfNeeded(
statements: Statement[],
ctor: ConstructorDeclaration | undefined,
hasExtendsClause: boolean,
hasSynthesizedSuper: boolean,
statementOffset: number) {
// If this isn't a derived class, just capture 'this' for arrow functions if necessary.
if (!hasExtendsClause) {
if (ctor) {
addCaptureThisForNodeIfNeeded(statements, ctor);
}
return SuperCaptureResult.NoReplacement;
}
// We must be here because the user didn't write a constructor
// but we needed to call 'super(...args)' anyway as per 14.5.14 of the ES2016 spec.
// If that's the case we can just immediately return the result of a 'super()' call.
if (!ctor) {
statements.push(createReturn(createDefaultSuperCallOrThis()));
return SuperCaptureResult.ReplaceWithReturn;
}
// The constructor exists, but it and the 'super()' call it contains were generated
// for something like property initializers.
// Create a captured '_this' variable and assume it will subsequently be used.
if (hasSynthesizedSuper) {
captureThisForNode(statements, ctor, createDefaultSuperCallOrThis());
enableSubstitutionsForCapturedThis();
return SuperCaptureResult.ReplaceSuperCapture;
}
// Most of the time, a 'super' call will be the first real statement in a constructor body.
// In these cases, we'd like to transform these into a *single* statement instead of a declaration
// followed by an assignment statement for '_this'. For instance, if we emitted without an initializer,
// we'd get:
//
// var _this;
// _this = _super.call(...) || this;
//
// instead of
//
// var _this = _super.call(...) || this;
//
// Additionally, if the 'super()' call is the last statement, we should just avoid capturing
// entirely and immediately return the result like so:
//
// return _super.call(...) || this;
//
let firstStatement: Statement;
let superCallExpression: Expression;
const ctorStatements = ctor.body.statements;
if (statementOffset < ctorStatements.length) {
firstStatement = ctorStatements[statementOffset];
if (firstStatement.kind === SyntaxKind.ExpressionStatement && isSuperCallExpression((firstStatement as ExpressionStatement).expression)) {
const superCall = (firstStatement as ExpressionStatement).expression as CallExpression;
superCallExpression = setOriginalNode(
saveStateAndInvoke(superCall, visitImmediateSuperCallInBody),
superCall
);
}
}
// Return the result if we have an immediate super() call on the last statement.
if (superCallExpression && statementOffset === ctorStatements.length - 1) {
statements.push(createReturn(superCallExpression));
return SuperCaptureResult.ReplaceWithReturn;
}
// Perform the capture.
captureThisForNode(statements, ctor, superCallExpression, firstStatement);
// If we're actually replacing the original statement, we need to signal this to the caller.
if (superCallExpression) {
return SuperCaptureResult.ReplaceSuperCapture;
}
return SuperCaptureResult.NoReplacement;
}
function createDefaultSuperCallOrThis() {
const actualThis = createThis();
setEmitFlags(actualThis, EmitFlags.NoSubstitution);
const superCall = createFunctionApply(
createIdentifier("_super"),
actualThis,
createIdentifier("arguments"),
);
return createLogicalOr(superCall, actualThis);
}
/**
@@ -967,27 +1113,27 @@ namespace ts {
// of an initializer, we must emit that expression to preserve side effects.
if (name.elements.length > 0) {
statements.push(
setNodeEmitFlags(
setEmitFlags(
createVariableStatement(
/*modifiers*/ undefined,
createVariableDeclarationList(
flattenParameterDestructuring(context, parameter, temp, visitor)
)
),
NodeEmitFlags.CustomPrologue
EmitFlags.CustomPrologue
)
);
}
else if (initializer) {
statements.push(
setNodeEmitFlags(
setEmitFlags(
createStatement(
createAssignment(
temp,
visitNode(initializer, visitor, isExpression)
)
),
NodeEmitFlags.CustomPrologue
EmitFlags.CustomPrologue
)
);
}
@@ -1008,23 +1154,23 @@ namespace ts {
getSynthesizedClone(name),
createVoidZero()
),
setNodeEmitFlags(
setEmitFlags(
createBlock([
createStatement(
createAssignment(
setNodeEmitFlags(getMutableClone(name), NodeEmitFlags.NoSourceMap),
setNodeEmitFlags(initializer, NodeEmitFlags.NoSourceMap | getNodeEmitFlags(initializer)),
setEmitFlags(getMutableClone(name), EmitFlags.NoSourceMap),
setEmitFlags(initializer, EmitFlags.NoSourceMap | getEmitFlags(initializer)),
/*location*/ parameter
)
)
], /*location*/ parameter),
NodeEmitFlags.SingleLine | NodeEmitFlags.NoTrailingSourceMap | NodeEmitFlags.NoTokenSourceMaps
EmitFlags.SingleLine | EmitFlags.NoTrailingSourceMap | EmitFlags.NoTokenSourceMaps
),
/*elseStatement*/ undefined,
/*location*/ parameter
);
statement.startsOnNewLine = true;
setNodeEmitFlags(statement, NodeEmitFlags.NoTokenSourceMaps | NodeEmitFlags.NoTrailingSourceMap | NodeEmitFlags.CustomPrologue);
setEmitFlags(statement, EmitFlags.NoTokenSourceMaps | EmitFlags.NoTrailingSourceMap | EmitFlags.CustomPrologue);
statements.push(statement);
}
@@ -1057,7 +1203,7 @@ namespace ts {
// `declarationName` is the name of the local declaration for the parameter.
const declarationName = getMutableClone(<Identifier>parameter.name);
setNodeEmitFlags(declarationName, NodeEmitFlags.NoSourceMap);
setEmitFlags(declarationName, EmitFlags.NoSourceMap);
// `expressionName` is the name of the parameter used in expressions.
const expressionName = getSynthesizedClone(<Identifier>parameter.name);
@@ -1066,7 +1212,7 @@ namespace ts {
// var param = [];
statements.push(
setNodeEmitFlags(
setEmitFlags(
createVariableStatement(
/*modifiers*/ undefined,
createVariableDeclarationList([
@@ -1078,7 +1224,7 @@ namespace ts {
]),
/*location*/ parameter
),
NodeEmitFlags.CustomPrologue
EmitFlags.CustomPrologue
)
);
@@ -1111,7 +1257,7 @@ namespace ts {
])
);
setNodeEmitFlags(forStatement, NodeEmitFlags.CustomPrologue);
setEmitFlags(forStatement, EmitFlags.CustomPrologue);
startOnNewLine(forStatement);
statements.push(forStatement);
}
@@ -1124,24 +1270,29 @@ namespace ts {
*/
function addCaptureThisForNodeIfNeeded(statements: Statement[], node: Node): void {
if (node.transformFlags & TransformFlags.ContainsCapturedLexicalThis && node.kind !== SyntaxKind.ArrowFunction) {
enableSubstitutionsForCapturedThis();
const captureThisStatement = createVariableStatement(
/*modifiers*/ undefined,
createVariableDeclarationList([
createVariableDeclaration(
"_this",
/*type*/ undefined,
createThis()
)
])
);
setNodeEmitFlags(captureThisStatement, NodeEmitFlags.NoComments | NodeEmitFlags.CustomPrologue);
setSourceMapRange(captureThisStatement, node);
statements.push(captureThisStatement);
captureThisForNode(statements, node, createThis());
}
}
function captureThisForNode(statements: Statement[], node: Node, initializer: Expression | undefined, originalStatement?: Statement): void {
enableSubstitutionsForCapturedThis();
const captureThisStatement = createVariableStatement(
/*modifiers*/ undefined,
createVariableDeclarationList([
createVariableDeclaration(
"_this",
/*type*/ undefined,
initializer
)
]),
originalStatement
);
setEmitFlags(captureThisStatement, EmitFlags.NoComments | EmitFlags.CustomPrologue);
setSourceMapRange(captureThisStatement, node);
statements.push(captureThisStatement);
}
/**
* Adds statements to the class body function for a class to define the members of the
* class.
@@ -1200,7 +1351,7 @@ namespace ts {
const sourceMapRange = getSourceMapRange(member);
const func = transformFunctionLikeToExpression(member, /*location*/ member, /*name*/ undefined);
setNodeEmitFlags(func, NodeEmitFlags.NoComments);
setEmitFlags(func, EmitFlags.NoComments);
setSourceMapRange(func, sourceMapRange);
const statement = createStatement(
@@ -1221,7 +1372,7 @@ namespace ts {
// The location for the statement is used to emit comments only.
// No source map should be emitted for this statement to align with the
// old emitter.
setNodeEmitFlags(statement, NodeEmitFlags.NoSourceMap);
setEmitFlags(statement, EmitFlags.NoSourceMap);
return statement;
}
@@ -1240,7 +1391,7 @@ namespace ts {
// The location for the statement is used to emit source maps only.
// No comments should be emitted for this statement to align with the
// old emitter.
setNodeEmitFlags(statement, NodeEmitFlags.NoComments);
setEmitFlags(statement, EmitFlags.NoComments);
return statement;
}
@@ -1254,11 +1405,11 @@ namespace ts {
// To align with source maps in the old emitter, the receiver and property name
// arguments are both mapped contiguously to the accessor name.
const target = getMutableClone(receiver);
setNodeEmitFlags(target, NodeEmitFlags.NoComments | NodeEmitFlags.NoTrailingSourceMap);
setEmitFlags(target, EmitFlags.NoComments | EmitFlags.NoTrailingSourceMap);
setSourceMapRange(target, firstAccessor.name);
const propertyName = createExpressionForPropertyName(visitNode(firstAccessor.name, visitor, isPropertyName));
setNodeEmitFlags(propertyName, NodeEmitFlags.NoComments | NodeEmitFlags.NoLeadingSourceMap);
setEmitFlags(propertyName, EmitFlags.NoComments | EmitFlags.NoLeadingSourceMap);
setSourceMapRange(propertyName, firstAccessor.name);
const properties: ObjectLiteralElementLike[] = [];
@@ -1309,7 +1460,7 @@ namespace ts {
}
const func = transformFunctionLikeToExpression(node, /*location*/ node, /*name*/ undefined);
setNodeEmitFlags(func, NodeEmitFlags.CapturesThis);
setEmitFlags(func, EmitFlags.CapturesThis);
return func;
}
@@ -1434,7 +1585,7 @@ namespace ts {
const expression = visitNode(body, visitor, isExpression);
const returnStatement = createReturn(expression, /*location*/ body);
setNodeEmitFlags(returnStatement, NodeEmitFlags.NoTokenSourceMaps | NodeEmitFlags.NoTrailingSourceMap | NodeEmitFlags.NoTrailingComments);
setEmitFlags(returnStatement, EmitFlags.NoTokenSourceMaps | EmitFlags.NoTrailingSourceMap | EmitFlags.NoTrailingComments);
statements.push(returnStatement);
// To align with the source map emit for the old emitter, we set a custom
@@ -1452,7 +1603,7 @@ namespace ts {
const block = createBlock(createNodeArray(statements, statementsLocation), node.body, multiLine);
if (!multiLine && singleLine) {
setNodeEmitFlags(block, NodeEmitFlags.SingleLine);
setEmitFlags(block, EmitFlags.SingleLine);
}
if (closeBraceLocation) {
@@ -1875,7 +2026,7 @@ namespace ts {
}
// The old emitter does not emit source maps for the expression
setNodeEmitFlags(expression, NodeEmitFlags.NoSourceMap | getNodeEmitFlags(expression));
setEmitFlags(expression, EmitFlags.NoSourceMap | getEmitFlags(expression));
// The old emitter does not emit source maps for the block.
// We add the location to preserve comments.
@@ -1884,7 +2035,7 @@ namespace ts {
/*location*/ bodyLocation
);
setNodeEmitFlags(body, NodeEmitFlags.NoSourceMap | NodeEmitFlags.NoTokenSourceMaps);
setEmitFlags(body, EmitFlags.NoSourceMap | EmitFlags.NoTokenSourceMaps);
const forStatement = createFor(
createVariableDeclarationList([
@@ -1902,7 +2053,7 @@ namespace ts {
);
// Disable trailing source maps for the OpenParenToken to align source map emit with the old emitter.
setNodeEmitFlags(forStatement, NodeEmitFlags.NoTokenTrailingSourceMaps);
setEmitFlags(forStatement, EmitFlags.NoTokenTrailingSourceMaps);
return forStatement;
}
@@ -1938,13 +2089,13 @@ namespace ts {
const expressions: Expression[] = [];
const assignment = createAssignment(
temp,
setNodeEmitFlags(
setEmitFlags(
createObjectLiteral(
visitNodes(properties, visitor, isObjectLiteralElementLike, 0, numInitialProperties),
/*location*/ undefined,
node.multiLine
),
NodeEmitFlags.Indented
EmitFlags.Indented
)
);
if (node.multiLine) {
@@ -2067,16 +2218,16 @@ namespace ts {
const isAsyncBlockContainingAwait =
enclosingNonArrowFunction
&& (enclosingNonArrowFunction.emitFlags & NodeEmitFlags.AsyncFunctionBody) !== 0
&& (getEmitFlags(enclosingNonArrowFunction) & EmitFlags.AsyncFunctionBody) !== 0
&& (node.statement.transformFlags & TransformFlags.ContainsYield) !== 0;
let loopBodyFlags: NodeEmitFlags = 0;
let loopBodyFlags: EmitFlags = 0;
if (currentState.containsLexicalThis) {
loopBodyFlags |= NodeEmitFlags.CapturesThis;
loopBodyFlags |= EmitFlags.CapturesThis;
}
if (isAsyncBlockContainingAwait) {
loopBodyFlags |= NodeEmitFlags.AsyncFunctionBody;
loopBodyFlags |= EmitFlags.AsyncFunctionBody;
}
const convertedLoopVariable =
@@ -2087,7 +2238,7 @@ namespace ts {
createVariableDeclaration(
functionName,
/*type*/ undefined,
setNodeEmitFlags(
setEmitFlags(
createFunctionExpression(
isAsyncBlockContainingAwait ? createToken(SyntaxKind.AsteriskToken) : undefined,
/*name*/ undefined,
@@ -2480,7 +2631,7 @@ namespace ts {
// Methods with computed property names are handled in visitObjectLiteralExpression.
Debug.assert(!isComputedPropertyName(node.name));
const functionExpression = transformFunctionLikeToExpression(node, /*location*/ moveRangePos(node, -1), /*name*/ undefined);
setNodeEmitFlags(functionExpression, NodeEmitFlags.NoLeadingComments | getNodeEmitFlags(functionExpression));
setEmitFlags(functionExpression, EmitFlags.NoLeadingComments | getEmitFlags(functionExpression));
return createPropertyAssignment(
node.name,
functionExpression,
@@ -2526,11 +2677,23 @@ namespace ts {
*
* @param node a CallExpression.
*/
function visitCallExpression(node: CallExpression): LeftHandSideExpression {
function visitCallExpression(node: CallExpression) {
return visitCallExpressionWithPotentialCapturedThisAssignment(node, /*assignToCapturedThis*/ true);
}
function visitImmediateSuperCallInBody(node: CallExpression) {
return visitCallExpressionWithPotentialCapturedThisAssignment(node, /*assignToCapturedThis*/ false);
}
function visitCallExpressionWithPotentialCapturedThisAssignment(node: CallExpression, assignToCapturedThis: boolean): CallExpression | BinaryExpression {
// We are here either because SuperKeyword was used somewhere in the expression, or
// because we contain a SpreadElementExpression.
const { target, thisArg } = createCallBinding(node.expression, hoistVariableDeclaration);
if (node.expression.kind === SyntaxKind.SuperKeyword) {
setEmitFlags(thisArg, EmitFlags.NoSubstitution);
}
let resultingCall: CallExpression | BinaryExpression;
if (node.transformFlags & TransformFlags.ContainsSpreadElementExpression) {
// [source]
// f(...a, b)
@@ -2546,7 +2709,7 @@ namespace ts {
// _super.m.apply(this, a.concat([b]))
// _super.prototype.m.apply(this, a.concat([b]))
return createFunctionApply(
resultingCall = createFunctionApply(
visitNode(target, visitor, isExpression),
visitNode(thisArg, visitor, isExpression),
transformAndSpreadElements(node.arguments, /*needsUniqueCopy*/ false, /*multiLine*/ false, /*hasTrailingComma*/ false)
@@ -2563,13 +2726,27 @@ namespace ts {
// _super.m.call(this, a)
// _super.prototype.m.call(this, a)
return createFunctionCall(
resultingCall = createFunctionCall(
visitNode(target, visitor, isExpression),
visitNode(thisArg, visitor, isExpression),
visitNodes(node.arguments, visitor, isExpression),
/*location*/ node
);
}
if (node.expression.kind === SyntaxKind.SuperKeyword) {
const actualThis = createThis();
setEmitFlags(actualThis, EmitFlags.NoSubstitution);
const initializer =
createLogicalOr(
resultingCall,
actualThis
);
return assignToCapturedThis
? createAssignment(createIdentifier("_this"), initializer)
: initializer;
}
return resultingCall;
}
/**
@@ -2855,7 +3032,7 @@ namespace ts {
*
* @param node The node to be printed.
*/
function onEmitNode(node: Node, emit: (node: Node) => void) {
function onEmitNode(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void) {
const savedEnclosingFunction = enclosingFunction;
if (enabledSubstitutions & ES6SubstitutionFlags.CapturedThis && isFunctionLike(node)) {
@@ -2863,7 +3040,7 @@ namespace ts {
enclosingFunction = node;
}
previousOnEmitNode(node, emit);
previousOnEmitNode(emitContext, node, emitCallback);
enclosingFunction = savedEnclosingFunction;
}
@@ -2904,10 +3081,10 @@ namespace ts {
* @param isExpression A value indicating whether the node is to be used in an expression
* position.
*/
function onSubstituteNode(node: Node, isExpression: boolean) {
node = previousOnSubstituteNode(node, isExpression);
function onSubstituteNode(emitContext: EmitContext, node: Node) {
node = previousOnSubstituteNode(emitContext, node);
if (isExpression) {
if (emitContext === EmitContext.Expression) {
return substituteExpression(node);
}
@@ -2995,7 +3172,7 @@ namespace ts {
function substituteThisKeyword(node: PrimaryExpression): PrimaryExpression {
if (enabledSubstitutions & ES6SubstitutionFlags.CapturedThis
&& enclosingFunction
&& enclosingFunction.emitFlags & NodeEmitFlags.CapturesThis) {
&& getEmitFlags(enclosingFunction) & EmitFlags.CapturesThis) {
return createIdentifier("_this", /*location*/ node);
}
@@ -3013,7 +3190,7 @@ namespace ts {
* @param allowSourceMaps A value indicating whether source maps may be emitted for the name.
*/
function getLocalName(node: ClassDeclaration | ClassExpression | FunctionDeclaration, allowComments?: boolean, allowSourceMaps?: boolean) {
return getDeclarationName(node, allowComments, allowSourceMaps, NodeEmitFlags.LocalName);
return getDeclarationName(node, allowComments, allowSourceMaps, EmitFlags.LocalName);
}
/**
@@ -3022,18 +3199,18 @@ namespace ts {
* @param node The declaration.
* @param allowComments Allow comments for the name.
*/
function getDeclarationName(node: DeclarationStatement | ClassExpression, allowComments?: boolean, allowSourceMaps?: boolean, emitFlags?: NodeEmitFlags) {
function getDeclarationName(node: DeclarationStatement | ClassExpression, allowComments?: boolean, allowSourceMaps?: boolean, emitFlags?: EmitFlags) {
if (node.name && !isGeneratedIdentifier(node.name)) {
const name = getMutableClone(node.name);
emitFlags |= getNodeEmitFlags(node.name);
emitFlags |= getEmitFlags(node.name);
if (!allowSourceMaps) {
emitFlags |= NodeEmitFlags.NoSourceMap;
emitFlags |= EmitFlags.NoSourceMap;
}
if (!allowComments) {
emitFlags |= NodeEmitFlags.NoComments;
emitFlags |= EmitFlags.NoComments;
}
if (emitFlags) {
setNodeEmitFlags(name, emitFlags);
setEmitFlags(name, emitFlags);
}
return name;
}
+4
View File
@@ -9,6 +9,10 @@ namespace ts {
return transformSourceFile;
function transformSourceFile(node: SourceFile) {
if (isDeclarationFile(node)) {
return node;
}
return visitEachChild(node, visitor, context);
}
+12 -11
View File
@@ -231,9 +231,6 @@ namespace ts {
endLexicalEnvironment,
hoistFunctionDeclaration,
hoistVariableDeclaration,
setSourceMapRange,
setCommentRange,
setNodeEmitFlags
} = context;
const compilerOptions = context.getCompilerOptions();
@@ -294,6 +291,10 @@ namespace ts {
return transformSourceFile;
function transformSourceFile(node: SourceFile) {
if (isDeclarationFile(node)) {
return node;
}
if (node.transformFlags & TransformFlags.ContainsGenerator) {
currentSourceFile = node;
node = visitEachChild(node, visitor, context);
@@ -444,7 +445,7 @@ namespace ts {
*/
function visitFunctionDeclaration(node: FunctionDeclaration): Statement {
// Currently, we only support generators that were originally async functions.
if (node.asteriskToken && node.emitFlags & NodeEmitFlags.AsyncFunctionBody) {
if (node.asteriskToken && getEmitFlags(node) & EmitFlags.AsyncFunctionBody) {
node = setOriginalNode(
createFunctionDeclaration(
/*decorators*/ undefined,
@@ -492,7 +493,7 @@ namespace ts {
*/
function visitFunctionExpression(node: FunctionExpression): Expression {
// Currently, we only support generators that were originally async functions.
if (node.asteriskToken && node.emitFlags & NodeEmitFlags.AsyncFunctionBody) {
if (node.asteriskToken && getEmitFlags(node) & EmitFlags.AsyncFunctionBody) {
node = setOriginalNode(
createFunctionExpression(
/*asteriskToken*/ undefined,
@@ -616,7 +617,7 @@ namespace ts {
}
else {
// Do not hoist custom prologues.
if (node.emitFlags & NodeEmitFlags.CustomPrologue) {
if (getEmitFlags(node) & EmitFlags.CustomPrologue) {
return node;
}
@@ -1887,9 +1888,9 @@ namespace ts {
return -1;
}
function onSubstituteNode(node: Node, isExpression: boolean): Node {
node = previousOnSubstituteNode(node, isExpression);
if (isExpression) {
function onSubstituteNode(emitContext: EmitContext, node: Node): Node {
node = previousOnSubstituteNode(emitContext, node);
if (emitContext === EmitContext.Expression) {
return substituteExpression(<Expression>node);
}
return node;
@@ -2585,7 +2586,7 @@ namespace ts {
/*typeArguments*/ undefined,
[
createThis(),
setNodeEmitFlags(
setEmitFlags(
createFunctionExpression(
/*asteriskToken*/ undefined,
/*name*/ undefined,
@@ -2598,7 +2599,7 @@ namespace ts {
/*multiLine*/ buildResult.length > 0
)
),
NodeEmitFlags.ReuseTempVariableScope
EmitFlags.ReuseTempVariableScope
)
]
);
+4
View File
@@ -16,6 +16,10 @@ namespace ts {
* @param node A SourceFile node.
*/
function transformSourceFile(node: SourceFile) {
if (isDeclarationFile(node)) {
return node;
}
currentSourceFile = node;
node = visitEachChild(node, visitor, context);
currentSourceFile = undefined;
+4
View File
@@ -12,6 +12,10 @@ namespace ts {
return transformSourceFile;
function transformSourceFile(node: SourceFile) {
if (isDeclarationFile(node)) {
return node;
}
if (isExternalModule(node) || compilerOptions.isolatedModules) {
currentSourceFile = node;
return visitEachChild(node, visitor, context);
+26 -25
View File
@@ -15,9 +15,6 @@ namespace ts {
startLexicalEnvironment,
endLexicalEnvironment,
hoistVariableDeclaration,
setNodeEmitFlags,
getNodeEmitFlags,
setSourceMapRange,
} = context;
const compilerOptions = context.getCompilerOptions();
@@ -54,6 +51,10 @@ namespace ts {
* @param node The SourceFile node.
*/
function transformSourceFile(node: SourceFile) {
if (isDeclarationFile(node)) {
return node;
}
if (isExternalModule(node) || compilerOptions.isolatedModules) {
currentSourceFile = node;
@@ -92,7 +93,7 @@ namespace ts {
const updated = updateSourceFile(node, statements);
if (hasExportStarsToExportValues) {
setNodeEmitFlags(updated, NodeEmitFlags.EmitExportStar | getNodeEmitFlags(node));
setEmitFlags(updated, EmitFlags.EmitExportStar | getEmitFlags(node));
}
return updated;
@@ -116,7 +117,7 @@ namespace ts {
*/
function transformUMDModule(node: SourceFile) {
const define = createIdentifier("define");
setNodeEmitFlags(define, NodeEmitFlags.UMDDefine);
setEmitFlags(define, EmitFlags.UMDDefine);
return transformAsynchronousModule(node, define, /*moduleName*/ undefined, /*includeNonAmdDependencies*/ false);
}
@@ -220,7 +221,7 @@ namespace ts {
if (hasExportStarsToExportValues) {
// If we have any `export * from ...` declarations
// we need to inform the emitter to add the __export helper.
setNodeEmitFlags(body, NodeEmitFlags.EmitExportStar);
setEmitFlags(body, EmitFlags.EmitExportStar);
}
return body;
@@ -234,7 +235,7 @@ namespace ts {
/*location*/ exportEquals
);
setNodeEmitFlags(statement, NodeEmitFlags.NoTokenSourceMaps | NodeEmitFlags.NoComments);
setEmitFlags(statement, EmitFlags.NoTokenSourceMaps | EmitFlags.NoComments);
statements.push(statement);
}
else {
@@ -249,7 +250,7 @@ namespace ts {
/*location*/ exportEquals
);
setNodeEmitFlags(statement, NodeEmitFlags.NoComments);
setEmitFlags(statement, EmitFlags.NoComments);
statements.push(statement);
}
}
@@ -388,7 +389,7 @@ namespace ts {
// Set emitFlags on the name of the importEqualsDeclaration
// This is so the printer will not substitute the identifier
setNodeEmitFlags(node.name, NodeEmitFlags.NoSubstitution);
setEmitFlags(node.name, EmitFlags.NoSubstitution);
const statements: Statement[] = [];
if (moduleKind !== ModuleKind.AMD) {
if (hasModifier(node, ModifierFlags.Export)) {
@@ -598,7 +599,7 @@ namespace ts {
}
else {
statements.push(
createExportStatement(node.name, setNodeEmitFlags(getSynthesizedClone(node.name), NodeEmitFlags.LocalName), /*location*/ node)
createExportStatement(node.name, setEmitFlags(getSynthesizedClone(node.name), EmitFlags.LocalName), /*location*/ node)
);
}
}
@@ -813,7 +814,7 @@ namespace ts {
)],
/*location*/ node
);
setNodeEmitFlags(transformedStatement, NodeEmitFlags.NoComments);
setEmitFlags(transformedStatement, EmitFlags.NoComments);
statements.push(transformedStatement);
}
@@ -821,14 +822,14 @@ namespace ts {
return node.name ? getSynthesizedClone(node.name) : getGeneratedNameForNode(node);
}
function onEmitNode(node: Node, emit: (node: Node) => void): void {
function onEmitNode(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void): void {
if (node.kind === SyntaxKind.SourceFile) {
bindingNameExportSpecifiersMap = bindingNameExportSpecifiersForFileMap[getOriginalNodeId(node)];
previousOnEmitNode(node, emit);
previousOnEmitNode(emitContext, node, emitCallback);
bindingNameExportSpecifiersMap = undefined;
}
else {
previousOnEmitNode(node, emit);
previousOnEmitNode(emitContext, node, emitCallback);
}
}
@@ -839,9 +840,9 @@ namespace ts {
* @param isExpression A value indicating whether the node is to be used in an expression
* position.
*/
function onSubstituteNode(node: Node, isExpression: boolean) {
node = previousOnSubstituteNode(node, isExpression);
if (isExpression) {
function onSubstituteNode(emitContext: EmitContext, node: Node) {
node = previousOnSubstituteNode(emitContext, node);
if (emitContext === EmitContext.Expression) {
return substituteExpression(<Expression>node);
}
else if (isShorthandPropertyAssignment(node)) {
@@ -890,7 +891,7 @@ namespace ts {
// If the left-hand-side of the binaryExpression is an identifier and its is export through export Specifier
if (isIdentifier(left) && isAssignmentOperator(node.operatorToken.kind)) {
if (bindingNameExportSpecifiersMap && hasProperty(bindingNameExportSpecifiersMap, left.text)) {
setNodeEmitFlags(node, NodeEmitFlags.NoSubstitution);
setEmitFlags(node, EmitFlags.NoSubstitution);
let nestedExportAssignment: BinaryExpression;
for (const specifier of bindingNameExportSpecifiersMap[left.text]) {
nestedExportAssignment = nestedExportAssignment ?
@@ -910,7 +911,7 @@ namespace ts {
const operand = node.operand;
if (isIdentifier(operand) && bindingNameExportSpecifiersForFileMap) {
if (bindingNameExportSpecifiersMap && hasProperty(bindingNameExportSpecifiersMap, operand.text)) {
setNodeEmitFlags(node, NodeEmitFlags.NoSubstitution);
setEmitFlags(node, EmitFlags.NoSubstitution);
let transformedUnaryExpression: BinaryExpression;
if (node.kind === SyntaxKind.PostfixUnaryExpression) {
transformedUnaryExpression = createBinary(
@@ -920,7 +921,7 @@ namespace ts {
/*location*/ node
);
// We have to set no substitution flag here to prevent visit the binary expression and substitute it again as we will preform all necessary substitution in here
setNodeEmitFlags(transformedUnaryExpression, NodeEmitFlags.NoSubstitution);
setEmitFlags(transformedUnaryExpression, EmitFlags.NoSubstitution);
}
let nestedExportAssignment: BinaryExpression;
for (const specifier of bindingNameExportSpecifiersMap[operand.text]) {
@@ -935,9 +936,9 @@ namespace ts {
}
function trySubstituteExportedName(node: Identifier) {
const emitFlags = getNodeEmitFlags(node);
if ((emitFlags & NodeEmitFlags.LocalName) === 0) {
const container = resolver.getReferencedExportContainer(node, (emitFlags & NodeEmitFlags.ExportName) !== 0);
const emitFlags = getEmitFlags(node);
if ((emitFlags & EmitFlags.LocalName) === 0) {
const container = resolver.getReferencedExportContainer(node, (emitFlags & EmitFlags.ExportName) !== 0);
if (container) {
if (container.kind === SyntaxKind.SourceFile) {
return createPropertyAccess(
@@ -953,7 +954,7 @@ namespace ts {
}
function trySubstituteImportedName(node: Identifier): Expression {
if ((getNodeEmitFlags(node) & NodeEmitFlags.LocalName) === 0) {
if ((getEmitFlags(node) & EmitFlags.LocalName) === 0) {
const declaration = resolver.getReferencedImportDeclaration(node);
if (declaration) {
if (isImportClause(declaration)) {
@@ -1077,7 +1078,7 @@ namespace ts {
if (includeNonAmdDependencies && importAliasName) {
// Set emitFlags on the name of the classDeclaration
// This is so that when printer will not substitute the identifier
setNodeEmitFlags(importAliasName, NodeEmitFlags.NoSubstitution);
setEmitFlags(importAliasName, EmitFlags.NoSubstitution);
aliasedModuleNames.push(externalModuleName);
importAliasNames.push(createParameter(importAliasName));
}
+19 -17
View File
@@ -10,8 +10,6 @@ namespace ts {
}
const {
getNodeEmitFlags,
setNodeEmitFlags,
startLexicalEnvironment,
endLexicalEnvironment,
hoistVariableDeclaration,
@@ -50,6 +48,10 @@ namespace ts {
return transformSourceFile;
function transformSourceFile(node: SourceFile) {
if (isDeclarationFile(node)) {
return node;
}
if (isExternalModule(node) || compilerOptions.isolatedModules) {
currentSourceFile = node;
currentNode = node;
@@ -116,9 +118,9 @@ namespace ts {
createParameter(contextObjectForFile)
],
/*type*/ undefined,
setNodeEmitFlags(
setEmitFlags(
createBlock(statements, /*location*/ undefined, /*multiLine*/ true),
NodeEmitFlags.EmitEmitHelpers
EmitFlags.EmitEmitHelpers
)
);
@@ -135,7 +137,7 @@ namespace ts {
: [dependencies, body]
)
)
], /*nodeEmitFlags*/ ~NodeEmitFlags.EmitEmitHelpers & getNodeEmitFlags(node));
], /*nodeEmitFlags*/ ~EmitFlags.EmitEmitHelpers & getEmitFlags(node));
}
/**
@@ -984,14 +986,14 @@ namespace ts {
// Substitutions
//
function onEmitNode(node: Node, emit: (node: Node) => void): void {
function onEmitNode(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void): void {
if (node.kind === SyntaxKind.SourceFile) {
exportFunctionForFile = exportFunctionForFileMap[getOriginalNodeId(node)];
previousOnEmitNode(node, emit);
previousOnEmitNode(emitContext, node, emitCallback);
exportFunctionForFile = undefined;
}
else {
previousOnEmitNode(node, emit);
previousOnEmitNode(emitContext, node, emitCallback);
}
}
@@ -1002,9 +1004,9 @@ namespace ts {
* @param isExpression A value indicating whether the node is to be used in an expression
* position.
*/
function onSubstituteNode(node: Node, isExpression: boolean) {
node = previousOnSubstituteNode(node, isExpression);
if (isExpression) {
function onSubstituteNode(emitContext: EmitContext, node: Node) {
node = previousOnSubstituteNode(emitContext, node);
if (emitContext === EmitContext.Expression) {
return substituteExpression(<Expression>node);
}
@@ -1053,7 +1055,7 @@ namespace ts {
}
function substituteAssignmentExpression(node: BinaryExpression): Expression {
setNodeEmitFlags(node, NodeEmitFlags.NoSubstitution);
setEmitFlags(node, EmitFlags.NoSubstitution);
const left = node.left;
switch (left.kind) {
@@ -1176,7 +1178,7 @@ namespace ts {
const exportDeclaration = resolver.getReferencedExportContainer(<Identifier>operand);
if (exportDeclaration) {
const expr = createPrefix(node.operator, operand, node);
setNodeEmitFlags(expr, NodeEmitFlags.NoSubstitution);
setEmitFlags(expr, EmitFlags.NoSubstitution);
const call = createExportExpression(<Identifier>operand, expr);
if (node.kind === SyntaxKind.PrefixUnaryExpression) {
return call;
@@ -1241,7 +1243,7 @@ namespace ts {
]),
m,
createBlock([
setNodeEmitFlags(
setEmitFlags(
createIf(
condition,
createStatement(
@@ -1251,7 +1253,7 @@ namespace ts {
)
)
),
NodeEmitFlags.SingleLine
EmitFlags.SingleLine
)
])
),
@@ -1393,10 +1395,10 @@ namespace ts {
hoistBindingElement(node, /*isExported*/ false);
}
function updateSourceFile(node: SourceFile, statements: Statement[], nodeEmitFlags: NodeEmitFlags) {
function updateSourceFile(node: SourceFile, statements: Statement[], nodeEmitFlags: EmitFlags) {
const updated = getMutableClone(node);
updated.statements = createNodeArray(statements, node.statements);
setNodeEmitFlags(updated, nodeEmitFlags);
setEmitFlags(updated, nodeEmitFlags);
return updated;
}
}
+150 -67
View File
@@ -24,10 +24,6 @@ namespace ts {
export function transformTypeScript(context: TransformationContext) {
const {
getNodeEmitFlags,
setNodeEmitFlags,
setCommentRange,
setSourceMapRange,
startLexicalEnvironment,
endLexicalEnvironment,
hoistVariableDeclaration,
@@ -46,11 +42,16 @@ namespace ts {
context.onEmitNode = onEmitNode;
context.onSubstituteNode = onSubstituteNode;
// Enable substitution for property/element access to emit const enum values.
context.enableSubstitution(SyntaxKind.PropertyAccessExpression);
context.enableSubstitution(SyntaxKind.ElementAccessExpression);
// These variables contain state that changes as we descend into the tree.
let currentSourceFile: SourceFile;
let currentNamespace: ModuleDeclaration;
let currentNamespaceContainerName: Identifier;
let currentScope: SourceFile | Block | ModuleBlock | CaseBlock;
let currentScopeFirstDeclarationsOfName: Map<Node>;
let currentSourceFileExternalHelpersModuleName: Identifier;
/**
@@ -85,6 +86,10 @@ namespace ts {
* @param node A SourceFile node.
*/
function transformSourceFile(node: SourceFile) {
if (isDeclarationFile(node)) {
return node;
}
return visitNode(node, visitor, isSourceFile);
}
@@ -96,6 +101,7 @@ namespace ts {
function saveStateAndInvoke<T>(node: Node, f: (node: Node) => T): T {
// Save state
const savedCurrentScope = currentScope;
const savedCurrentScopeFirstDeclarationsOfName = currentScopeFirstDeclarationsOfName;
// Handle state changes before visiting a node.
onBeforeVisitNode(node);
@@ -103,8 +109,11 @@ namespace ts {
const visited = f(node);
// Restore state
currentScope = savedCurrentScope;
if (currentScope !== savedCurrentScope) {
currentScopeFirstDeclarationsOfName = savedCurrentScopeFirstDeclarationsOfName;
}
currentScope = savedCurrentScope;
return visited;
}
@@ -410,6 +419,16 @@ namespace ts {
case SyntaxKind.ModuleBlock:
case SyntaxKind.Block:
currentScope = <SourceFile | CaseBlock | ModuleBlock | Block>node;
currentScopeFirstDeclarationsOfName = undefined;
break;
case SyntaxKind.ClassDeclaration:
case SyntaxKind.FunctionDeclaration:
if (hasModifier(node, ModifierFlags.Ambient)) {
break;
}
recordEmittedDeclarationInScope(node);
break;
}
}
@@ -449,7 +468,7 @@ namespace ts {
node = visitEachChild(node, visitor, context);
}
setNodeEmitFlags(node, NodeEmitFlags.EmitEmitHelpers | node.emitFlags);
setEmitFlags(node, EmitFlags.EmitEmitHelpers | getEmitFlags(node));
return node;
}
@@ -521,7 +540,7 @@ namespace ts {
// To better align with the old emitter, we should not emit a trailing source map
// entry if the class has static properties.
if (staticProperties.length > 0) {
setNodeEmitFlags(classDeclaration, NodeEmitFlags.NoTrailingSourceMap | getNodeEmitFlags(classDeclaration));
setEmitFlags(classDeclaration, EmitFlags.NoTrailingSourceMap | getEmitFlags(classDeclaration));
}
statements.push(classDeclaration);
@@ -776,7 +795,7 @@ namespace ts {
// To preserve the behavior of the old emitter, we explicitly indent
// the body of a class with static initializers.
setNodeEmitFlags(classExpression, NodeEmitFlags.Indented | getNodeEmitFlags(classExpression));
setEmitFlags(classExpression, EmitFlags.Indented | getEmitFlags(classExpression));
expressions.push(startOnNewLine(createAssignment(temp, classExpression)));
addRange(expressions, generateInitializedPropertyExpressions(node, staticProperties, temp));
expressions.push(startOnNewLine(temp));
@@ -1009,10 +1028,10 @@ namespace ts {
Debug.assert(isIdentifier(node.name));
const name = node.name as Identifier;
const propertyName = getMutableClone(name);
setNodeEmitFlags(propertyName, NodeEmitFlags.NoComments | NodeEmitFlags.NoSourceMap);
setEmitFlags(propertyName, EmitFlags.NoComments | EmitFlags.NoSourceMap);
const localName = getMutableClone(name);
setNodeEmitFlags(localName, NodeEmitFlags.NoComments);
setEmitFlags(localName, EmitFlags.NoComments);
return startOnNewLine(
createStatement(
@@ -1418,7 +1437,7 @@ namespace ts {
moveRangePastDecorators(member)
);
setNodeEmitFlags(helper, NodeEmitFlags.NoComments);
setEmitFlags(helper, EmitFlags.NoComments);
return helper;
}
@@ -1467,7 +1486,7 @@ namespace ts {
);
const result = createAssignment(getDeclarationName(node), expression, moveRangePastDecorators(node));
setNodeEmitFlags(result, NodeEmitFlags.NoComments);
setEmitFlags(result, EmitFlags.NoComments);
return result;
}
// Emit the call to __decorate. Given the class:
@@ -1491,7 +1510,7 @@ namespace ts {
moveRangePastDecorators(node)
);
setNodeEmitFlags(result, NodeEmitFlags.NoComments);
setEmitFlags(result, EmitFlags.NoComments);
return result;
}
}
@@ -1521,7 +1540,7 @@ namespace ts {
transformDecorator(decorator),
parameterOffset,
/*location*/ decorator.expression);
setNodeEmitFlags(helper, NodeEmitFlags.NoComments);
setEmitFlags(helper, EmitFlags.NoComments);
expressions.push(helper);
}
}
@@ -2324,11 +2343,11 @@ namespace ts {
if (languageVersion >= ScriptTarget.ES6) {
if (resolver.getNodeCheckFlags(node) & NodeCheckFlags.AsyncMethodWithSuperBinding) {
enableSubstitutionForAsyncMethodsWithSuper();
setNodeEmitFlags(block, NodeEmitFlags.EmitAdvancedSuperHelper);
setEmitFlags(block, EmitFlags.EmitAdvancedSuperHelper);
}
else if (resolver.getNodeCheckFlags(node) & NodeCheckFlags.AsyncMethodWithSuper) {
enableSubstitutionForAsyncMethodsWithSuper();
setNodeEmitFlags(block, NodeEmitFlags.EmitSuperHelper);
setEmitFlags(block, EmitFlags.EmitSuperHelper);
}
}
@@ -2375,7 +2394,7 @@ namespace ts {
setOriginalNode(parameter, node);
setCommentRange(parameter, node);
setSourceMapRange(parameter, moveRangePastModifiers(node));
setNodeEmitFlags(parameter.name, NodeEmitFlags.NoTrailingSourceMap);
setEmitFlags(parameter.name, EmitFlags.NoTrailingSourceMap);
return parameter;
}
@@ -2498,10 +2517,12 @@ namespace ts {
}
function shouldEmitVarForEnumDeclaration(node: EnumDeclaration | ModuleDeclaration) {
return !hasModifier(node, ModifierFlags.Export)
|| (isES6ExportedDeclaration(node) && isFirstDeclarationOfKind(node, node.kind));
return isFirstEmittedDeclarationInScope(node)
&& (!hasModifier(node, ModifierFlags.Export)
|| isES6ExportedDeclaration(node));
}
/*
* Adds a trailing VariableStatement for an enum or module declaration.
*/
@@ -2534,17 +2555,18 @@ namespace ts {
// We request to be advised when the printer is about to print this node. This allows
// us to set up the correct state for later substitutions.
let emitFlags = NodeEmitFlags.AdviseOnEmitNode;
let emitFlags = EmitFlags.AdviseOnEmitNode;
// If needed, we should emit a variable declaration for the enum. If we emit
// a leading variable declaration, we should not emit leading comments for the
// enum body.
recordEmittedDeclarationInScope(node);
if (shouldEmitVarForEnumDeclaration(node)) {
addVarForEnumOrModuleDeclaration(statements, node);
// We should still emit the comments if we are emitting a system module.
if (moduleKind !== ModuleKind.System || currentScope !== currentSourceFile) {
emitFlags |= NodeEmitFlags.NoLeadingComments;
emitFlags |= EmitFlags.NoLeadingComments;
}
}
@@ -2584,7 +2606,7 @@ namespace ts {
);
setOriginalNode(enumStatement, node);
setNodeEmitFlags(enumStatement, emitFlags);
setEmitFlags(enumStatement, emitFlags);
statements.push(enumStatement);
if (isNamespaceExport(node)) {
@@ -2675,20 +2697,48 @@ namespace ts {
return isInstantiatedModule(node, compilerOptions.preserveConstEnums || compilerOptions.isolatedModules);
}
function isModuleMergedWithES6Class(node: ModuleDeclaration) {
return languageVersion === ScriptTarget.ES6
&& isMergedWithClass(node);
}
function isES6ExportedDeclaration(node: Node) {
return isExternalModuleExport(node)
&& moduleKind === ModuleKind.ES6;
}
/**
* Records that a declaration was emitted in the current scope, if it was the first
* declaration for the provided symbol.
*
* NOTE: if there is ever a transformation above this one, we may not be able to rely
* on symbol names.
*/
function recordEmittedDeclarationInScope(node: Node) {
const name = node.symbol && node.symbol.name;
if (name) {
if (!currentScopeFirstDeclarationsOfName) {
currentScopeFirstDeclarationsOfName = createMap<Node>();
}
if (!(name in currentScopeFirstDeclarationsOfName)) {
currentScopeFirstDeclarationsOfName[name] = node;
}
}
}
/**
* Determines whether a declaration is the first declaration with the same name emitted
* in the current scope.
*/
function isFirstEmittedDeclarationInScope(node: Node) {
if (currentScopeFirstDeclarationsOfName) {
const name = node.symbol && node.symbol.name;
if (name) {
return currentScopeFirstDeclarationsOfName[name] === node;
}
}
return false;
}
function shouldEmitVarForModuleDeclaration(node: ModuleDeclaration) {
return !isModuleMergedWithES6Class(node)
&& (!isES6ExportedDeclaration(node)
|| isFirstDeclarationOfKind(node, node.kind));
return isFirstEmittedDeclarationInScope(node);
}
/**
@@ -2736,7 +2786,7 @@ namespace ts {
// })(m1 || (m1 = {})); // trailing comment module
//
setCommentRange(statement, node);
setNodeEmitFlags(statement, NodeEmitFlags.NoTrailingComments);
setEmitFlags(statement, EmitFlags.NoTrailingComments);
statements.push(statement);
}
@@ -2759,16 +2809,17 @@ namespace ts {
// We request to be advised when the printer is about to print this node. This allows
// us to set up the correct state for later substitutions.
let emitFlags = NodeEmitFlags.AdviseOnEmitNode;
let emitFlags = EmitFlags.AdviseOnEmitNode;
// If needed, we should emit a variable declaration for the module. If we emit
// a leading variable declaration, we should not emit leading comments for the
// module body.
recordEmittedDeclarationInScope(node);
if (shouldEmitVarForModuleDeclaration(node)) {
addVarForEnumOrModuleDeclaration(statements, node);
// We should still emit the comments if we are emitting a system module.
if (moduleKind !== ModuleKind.System || currentScope !== currentSourceFile) {
emitFlags |= NodeEmitFlags.NoLeadingComments;
emitFlags |= EmitFlags.NoLeadingComments;
}
}
@@ -2820,7 +2871,7 @@ namespace ts {
);
setOriginalNode(moduleStatement, node);
setNodeEmitFlags(moduleStatement, emitFlags);
setEmitFlags(moduleStatement, emitFlags);
statements.push(moduleStatement);
return statements;
}
@@ -2833,8 +2884,10 @@ namespace ts {
function transformModuleBody(node: ModuleDeclaration, namespaceLocalName: Identifier): Block {
const savedCurrentNamespaceContainerName = currentNamespaceContainerName;
const savedCurrentNamespace = currentNamespace;
const savedCurrentScopeFirstDeclarationsOfName = currentScopeFirstDeclarationsOfName;
currentNamespaceContainerName = namespaceLocalName;
currentNamespace = node;
currentScopeFirstDeclarationsOfName = undefined;
const statements: Statement[] = [];
startLexicalEnvironment();
@@ -2861,10 +2914,12 @@ namespace ts {
const moduleBlock = <ModuleBlock>getInnerMostModuleDeclarationFromDottedModule(node).body;
statementsLocation = moveRangePos(moduleBlock.statements, -1);
}
addRange(statements, endLexicalEnvironment());
addRange(statements, endLexicalEnvironment());
currentNamespaceContainerName = savedCurrentNamespaceContainerName;
currentNamespace = savedCurrentNamespace;
currentScopeFirstDeclarationsOfName = savedCurrentScopeFirstDeclarationsOfName;
const block = createBlock(
createNodeArray(
statements,
@@ -2895,7 +2950,7 @@ namespace ts {
// })(hello || (hello = {}));
// We only want to emit comment on the namespace which contains block body itself, not the containing namespaces.
if (body.kind !== SyntaxKind.ModuleBlock) {
setNodeEmitFlags(block, block.emitFlags | NodeEmitFlags.NoComments);
setEmitFlags(block, getEmitFlags(block) | EmitFlags.NoComments);
}
return block;
}
@@ -2936,7 +2991,7 @@ namespace ts {
}
const moduleReference = createExpressionFromEntityName(<EntityName>node.moduleReference);
setNodeEmitFlags(moduleReference, NodeEmitFlags.NoComments | NodeEmitFlags.NoNestedComments);
setEmitFlags(moduleReference, EmitFlags.NoComments | EmitFlags.NoNestedComments);
if (isNamedExternalModuleExport(node) || !isNamespaceExport(node)) {
// export var ${name} = ${moduleReference};
@@ -3048,15 +3103,15 @@ namespace ts {
function getNamespaceMemberName(name: Identifier, allowComments?: boolean, allowSourceMaps?: boolean): Expression {
const qualifiedName = createPropertyAccess(currentNamespaceContainerName, getSynthesizedClone(name), /*location*/ name);
let emitFlags: NodeEmitFlags;
let emitFlags: EmitFlags;
if (!allowComments) {
emitFlags |= NodeEmitFlags.NoComments;
emitFlags |= EmitFlags.NoComments;
}
if (!allowSourceMaps) {
emitFlags |= NodeEmitFlags.NoSourceMap;
emitFlags |= EmitFlags.NoSourceMap;
}
if (emitFlags) {
setNodeEmitFlags(qualifiedName, emitFlags);
setEmitFlags(qualifiedName, emitFlags);
}
return qualifiedName;
}
@@ -3093,7 +3148,7 @@ namespace ts {
* @param allowComments A value indicating whether comments may be emitted for the name.
*/
function getLocalName(node: DeclarationStatement | ClassExpression, noSourceMaps?: boolean, allowComments?: boolean) {
return getDeclarationName(node, allowComments, !noSourceMaps, NodeEmitFlags.LocalName);
return getDeclarationName(node, allowComments, !noSourceMaps, EmitFlags.LocalName);
}
/**
@@ -3111,7 +3166,7 @@ namespace ts {
return getNamespaceMemberName(getDeclarationName(node), allowComments, !noSourceMaps);
}
return getDeclarationName(node, allowComments, !noSourceMaps, NodeEmitFlags.ExportName);
return getDeclarationName(node, allowComments, !noSourceMaps, EmitFlags.ExportName);
}
/**
@@ -3122,20 +3177,20 @@ namespace ts {
* @param allowSourceMaps A value indicating whether source maps may be emitted for the name.
* @param emitFlags Additional NodeEmitFlags to specify for the name.
*/
function getDeclarationName(node: DeclarationStatement | ClassExpression, allowComments?: boolean, allowSourceMaps?: boolean, emitFlags?: NodeEmitFlags) {
function getDeclarationName(node: DeclarationStatement | ClassExpression, allowComments?: boolean, allowSourceMaps?: boolean, emitFlags?: EmitFlags) {
if (node.name) {
const name = getMutableClone(node.name);
emitFlags |= getNodeEmitFlags(node.name);
emitFlags |= getEmitFlags(node.name);
if (!allowSourceMaps) {
emitFlags |= NodeEmitFlags.NoSourceMap;
emitFlags |= EmitFlags.NoSourceMap;
}
if (!allowComments) {
emitFlags |= NodeEmitFlags.NoComments;
emitFlags |= EmitFlags.NoComments;
}
if (emitFlags) {
setNodeEmitFlags(name, emitFlags);
setEmitFlags(name, emitFlags);
}
return name;
@@ -3231,7 +3286,7 @@ namespace ts {
* @param node The node to emit.
* @param emit A callback used to emit the node in the printer.
*/
function onEmitNode(node: Node, emit: (node: Node) => void): void {
function onEmitNode(emitContext: EmitContext, node: Node, emitCallback: (emitContext: EmitContext, node: Node) => void): void {
const savedApplicableSubstitutions = applicableSubstitutions;
const savedCurrentSuperContainer = currentSuperContainer;
// If we need to support substitutions for `super` in an async method,
@@ -3248,7 +3303,7 @@ namespace ts {
applicableSubstitutions |= TypeScriptSubstitutionFlags.NonQualifiedEnumMembers;
}
previousOnEmitNode(node, emit);
previousOnEmitNode(emitContext, node, emitCallback);
applicableSubstitutions = savedApplicableSubstitutions;
currentSuperContainer = savedCurrentSuperContainer;
@@ -3261,9 +3316,9 @@ namespace ts {
* @param isExpression A value indicating whether the node is to be used in an expression
* position.
*/
function onSubstituteNode(node: Node, isExpression: boolean) {
node = previousOnSubstituteNode(node, isExpression);
if (isExpression) {
function onSubstituteNode(emitContext: EmitContext, node: Node) {
node = previousOnSubstituteNode(emitContext, node);
if (emitContext === EmitContext.Expression) {
return substituteExpression(<Expression>node);
}
else if (isShorthandPropertyAssignment(node)) {
@@ -3294,17 +3349,15 @@ namespace ts {
switch (node.kind) {
case SyntaxKind.Identifier:
return substituteExpressionIdentifier(<Identifier>node);
}
if (enabledSubstitutions & TypeScriptSubstitutionFlags.AsyncMethodsWithSuper) {
switch (node.kind) {
case SyntaxKind.CallExpression:
case SyntaxKind.PropertyAccessExpression:
return substitutePropertyAccessExpression(<PropertyAccessExpression>node);
case SyntaxKind.ElementAccessExpression:
return substituteElementAccessExpression(<ElementAccessExpression>node);
case SyntaxKind.CallExpression:
if (enabledSubstitutions & TypeScriptSubstitutionFlags.AsyncMethodsWithSuper) {
return substituteCallExpression(<CallExpression>node);
case SyntaxKind.PropertyAccessExpression:
return substitutePropertyAccessExpression(<PropertyAccessExpression>node);
case SyntaxKind.ElementAccessExpression:
return substituteElementAccessExpression(<ElementAccessExpression>node);
}
}
break;
}
return node;
@@ -3342,7 +3395,7 @@ namespace ts {
function trySubstituteNamespaceExportedName(node: Identifier): Expression {
// If this is explicitly a local name, do not substitute.
if (enabledSubstitutions & applicableSubstitutions && (getNodeEmitFlags(node) & NodeEmitFlags.LocalName) === 0) {
if (enabledSubstitutions & applicableSubstitutions && (getEmitFlags(node) & EmitFlags.LocalName) === 0) {
// If we are nested within a namespace declaration, we may need to qualifiy
// an identifier that is exported from a merged namespace.
const container = resolver.getReferencedExportContainer(node, /*prefixLocals*/ false);
@@ -3381,7 +3434,7 @@ namespace ts {
}
function substitutePropertyAccessExpression(node: PropertyAccessExpression) {
if (node.expression.kind === SyntaxKind.SuperKeyword) {
if (enabledSubstitutions & TypeScriptSubstitutionFlags.AsyncMethodsWithSuper && node.expression.kind === SyntaxKind.SuperKeyword) {
const flags = getSuperContainerAsyncMethodFlags();
if (flags) {
return createSuperAccessInAsyncMethod(
@@ -3392,11 +3445,11 @@ namespace ts {
}
}
return node;
return substituteConstantValue(node);
}
function substituteElementAccessExpression(node: ElementAccessExpression) {
if (node.expression.kind === SyntaxKind.SuperKeyword) {
if (enabledSubstitutions & TypeScriptSubstitutionFlags.AsyncMethodsWithSuper && node.expression.kind === SyntaxKind.SuperKeyword) {
const flags = getSuperContainerAsyncMethodFlags();
if (flags) {
return createSuperAccessInAsyncMethod(
@@ -3407,9 +3460,39 @@ namespace ts {
}
}
return substituteConstantValue(node);
}
function substituteConstantValue(node: PropertyAccessExpression | ElementAccessExpression): LeftHandSideExpression {
const constantValue = tryGetConstEnumValue(node);
if (constantValue !== undefined) {
const substitute = createLiteral(constantValue);
setSourceMapRange(substitute, node);
setCommentRange(substitute, node);
if (!compilerOptions.removeComments) {
const propertyName = isPropertyAccessExpression(node)
? declarationNameToString(node.name)
: getTextOfNode(node.argumentExpression);
substitute.trailingComment = ` ${propertyName} `;
}
setConstantValue(node, constantValue);
return substitute;
}
return node;
}
function tryGetConstEnumValue(node: Node): number {
if (compilerOptions.isolatedModules) {
return undefined;
}
return isPropertyAccessExpression(node) || isElementAccessExpression(node)
? resolver.getConstantValue(<PropertyAccessExpression | ElementAccessExpression>node)
: undefined;
}
function createSuperAccessInAsyncMethod(argumentExpression: Expression, flags: NodeCheckFlags, location: TextRange): LeftHandSideExpression {
if (flags & NodeCheckFlags.AsyncMethodWithSuperBinding) {
return createPropertyAccess(
+20 -5
View File
@@ -494,10 +494,7 @@ namespace ts {
/* @internal */ nextContainer?: Node; // Next container in declaration order (initialized by binding)
/* @internal */ localSymbol?: Symbol; // Local symbol declared by node (initialized by binding only for exported nodes)
/* @internal */ flowNode?: FlowNode; // Associated FlowNode (initialized by binding)
/* @internal */ transformId?: number; // Associates transient transformation properties with a specific transformation (initialized by transformation).
/* @internal */ emitFlags?: NodeEmitFlags; // Transient emit flags for a synthesized node (initialized by transformation).
/* @internal */ sourceMapRange?: TextRange; // Transient custom sourcemap range for a synthesized node (initialized by transformation).
/* @internal */ commentRange?: TextRange; // Transient custom comment range for a synthesized node (initialized by transformation).
/* @internal */ emitNode?: EmitNode; // Associated EmitNode (initialized by transforms)
}
export interface NodeArray<T extends Node> extends Array<T>, TextRange {
@@ -3175,7 +3172,17 @@ namespace ts {
}
/* @internal */
export const enum NodeEmitFlags {
export interface EmitNode {
flags?: EmitFlags;
commentRange?: TextRange;
sourceMapRange?: TextRange;
tokenSourceMapRanges?: Map<TextRange>;
annotatedNodes?: Node[]; // Tracks Parse-tree nodes with EmitNodes for eventual cleanup.
constantValue?: number;
}
/* @internal */
export const enum EmitFlags {
EmitEmitHelpers = 1 << 0, // Any emit helpers should be written to this node.
EmitExportStar = 1 << 1, // The export * helper should be written to this node.
EmitSuperHelper = 1 << 2, // Emit the basic _super helper for async methods.
@@ -3205,6 +3212,14 @@ namespace ts {
CustomPrologue = 1 << 23, // Treat the statement as if it were a prologue directive (NOTE: Prologue directives are *not* transformed).
}
/* @internal */
export const enum EmitContext {
SourceFile, // Emitting a SourceFile
Expression, // Emitting an Expression
IdentifierName, // Emitting an IdentifierName
Unspecified, // Emitting an otherwise unspecified node
}
/** Additional context provided to `visitEachChild` */
/* @internal */
export interface LexicalEnvironment {
+4 -4
View File
@@ -982,11 +982,11 @@ namespace ts {
}
/**
* Given an super call\property node returns a closest node where either
* - super call\property is legal in the node and not legal in the parent node the node.
* Given an super call/property node, returns the closest node where
* - a super call/property access is legal in the node and not legal in the parent node the node.
* i.e. super call is legal in constructor but not legal in the class body.
* - node is arrow function (so caller might need to call getSuperContainer in case it needs to climb higher)
* - super call\property is definitely illegal in the node (but might be legal in some subnode)
* - the container is an arrow function (so caller might need to call getSuperContainer again in case it needs to climb higher)
* - a super call/property is definitely illegal in the container (but might be legal in some subnode)
* i.e. super property access is illegal in function declaration but can be legal in the statement list
*/
export function getSuperContainer(node: Node, stopOnFunctions: boolean): Node {
@@ -2045,4 +2045,22 @@ namespace ts.projectSystem {
assert.equal(snap.getLength(), expectedLength, "Incorrect snapshot size");
}
});
describe("Language service", () => {
it("should work correctly on case-sensitive file systems", () => {
const lib = {
path: "/a/Lib/lib.d.ts",
content: "let x: number"
};
const f = {
path: "/a/b/app.ts",
content: "let x = 1;"
};
const host = createServerHost([lib, f], { executingFilePath: "/a/Lib/tsc.js", useCaseSensitiveFileNames: true });
const projectService = createProjectService(host);
projectService.openClientFile(f.path);
projectService.checkNumberOfProjects({ inferredProjects: 1 });
projectService.inferredProjects[0].getLanguageService().getProgram();
});
});
}
+6 -1
View File
@@ -1001,9 +1001,14 @@ namespace ts.server {
}
getScriptInfoForNormalizedPath(fileName: NormalizedPath) {
return this.filenameToScriptInfo.get(normalizedPathToPath(fileName, this.host.getCurrentDirectory(), this.toCanonicalFileName));
return this.getScriptInfoForPath(normalizedPathToPath(fileName, this.host.getCurrentDirectory(), this.toCanonicalFileName));
}
getScriptInfoForPath(fileName: Path) {
return this.filenameToScriptInfo.get(fileName);
}
setHostConfiguration(args: protocol.ConfigureRequestArguments) {
if (args.file) {
const info = this.getScriptInfoForNormalizedPath(toNormalizedPath(args.file));
+7 -1
View File
@@ -215,7 +215,13 @@ namespace ts.server {
}
getScriptInfos() {
return map(this.program.getSourceFiles(), sourceFile => this.getScriptInfoLSHost(sourceFile.path));
return map(this.program.getSourceFiles(), sourceFile => {
const scriptInfo = this.projectService.getScriptInfoForPath(sourceFile.path);
if (!scriptInfo) {
Debug.assert(false, `scriptInfo for a file '${sourceFile.fileName}' is missing.`);
}
return scriptInfo;
});
}
getFileEmitOutput(info: ScriptInfo, emitOnlyDtsFiles: boolean) {
+1 -1
View File
@@ -947,7 +947,7 @@ namespace ts {
let lastTypesRootVersion = 0;
const useCaseSensitivefileNames = false;
const useCaseSensitivefileNames = host.useCaseSensitiveFileNames && host.useCaseSensitiveFileNames();
const cancellationToken = new CancellationTokenObject(host.getCancellationToken && host.getCancellationToken());
const currentDirectory = host.getCurrentDirectory();
@@ -56,7 +56,6 @@ var clodule1 = (function () {
}
return clodule1;
}());
var clodule1;
(function (clodule1) {
function f(x) { }
})(clodule1 || (clodule1 = {}));
@@ -65,7 +64,6 @@ var clodule2 = (function () {
}
return clodule2;
}());
var clodule2;
(function (clodule2) {
var x;
var D = (function () {
@@ -79,7 +77,6 @@ var clodule3 = (function () {
}
return clodule3;
}());
var clodule3;
(function (clodule3) {
clodule3.y = { id: T };
})(clodule3 || (clodule3 = {}));
@@ -88,7 +85,6 @@ var clodule4 = (function () {
}
return clodule4;
}());
var clodule4;
(function (clodule4) {
var D = (function () {
function D() {
@@ -22,7 +22,6 @@ var clodule = (function () {
clodule.fn = function (id) { };
return clodule;
}());
var clodule;
(function (clodule) {
// error: duplicate identifier expected
function fn(x, y) {
@@ -22,7 +22,6 @@ var clodule = (function () {
clodule.fn = function (id) { };
return clodule;
}());
var clodule;
(function (clodule) {
// error: duplicate identifier expected
function fn(x, y) {
@@ -22,7 +22,6 @@ var clodule = (function () {
clodule.sfn = function (id) { return 42; };
return clodule;
}());
var clodule;
(function (clodule) {
// error: duplicate identifier expected
function fn(x, y) {
@@ -31,7 +31,6 @@ var Point = (function () {
Point.Origin = function () { return { x: 0, y: 0 }; }; // unexpected error here bug 840246
return Point;
}());
var Point;
(function (Point) {
function Origin() { return null; } //expected duplicate identifier error
Point.Origin = Origin;
@@ -47,7 +46,6 @@ var A;
return Point;
}());
A.Point = Point;
var Point;
(function (Point) {
function Origin() { return ""; } //expected duplicate identifier error
Point.Origin = Origin;
@@ -31,7 +31,6 @@ var Point = (function () {
Point.Origin = function () { return { x: 0, y: 0 }; };
return Point;
}());
var Point;
(function (Point) {
function Origin() { return ""; } // not an error, since not exported
})(Point || (Point = {}));
@@ -46,7 +45,6 @@ var A;
return Point;
}());
A.Point = Point;
var Point;
(function (Point) {
function Origin() { return ""; } // not an error since not exported
})(Point = A.Point || (A.Point = {}));
@@ -31,7 +31,6 @@ var Point = (function () {
return Point;
}());
Point.Origin = { x: 0, y: 0 };
var Point;
(function (Point) {
Point.Origin = ""; //expected duplicate identifier error
})(Point || (Point = {}));
@@ -46,7 +45,6 @@ var A;
}());
Point.Origin = { x: 0, y: 0 };
A.Point = Point;
var Point;
(function (Point) {
Point.Origin = ""; //expected duplicate identifier error
})(Point = A.Point || (A.Point = {}));
@@ -31,7 +31,6 @@ var Point = (function () {
return Point;
}());
Point.Origin = { x: 0, y: 0 };
var Point;
(function (Point) {
var Origin = ""; // not an error, since not exported
})(Point || (Point = {}));
@@ -46,7 +45,6 @@ var A;
}());
Point.Origin = { x: 0, y: 0 };
A.Point = Point;
var Point;
(function (Point) {
var Origin = ""; // not an error since not exported
})(Point = A.Point || (A.Point = {}));
@@ -76,7 +76,6 @@ var A = (function () {
}
return A;
}());
var A;
(function (A) {
A.Instance = new A();
})(A || (A = {}));
@@ -22,7 +22,6 @@ var enumdule;
enumdule[enumdule["Red"] = 0] = "Red";
enumdule[enumdule["Blue"] = 1] = "Blue";
})(enumdule || (enumdule = {}));
var enumdule;
(function (enumdule) {
var Point = (function () {
function Point(x, y) {
@@ -38,7 +38,7 @@ var A;
var Point3d = (function (_super) {
__extends(Point3d, _super);
function Point3d() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Point3d;
}(Point));
@@ -41,7 +41,7 @@ var A;
var Point3d = (function (_super) {
__extends(Point3d, _super);
function Point3d() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Point3d;
}(Point));
@@ -72,7 +72,6 @@ var B;
return { x: 0, y: 0 };
}
B.Point = Point;
var Point;
(function (Point) {
Point.Origin = { x: 0, y: 0 };
})(Point = B.Point || (B.Point = {}));
@@ -28,7 +28,6 @@ var enumdule;
}());
enumdule.Point = Point;
})(enumdule || (enumdule = {}));
var enumdule;
(function (enumdule) {
enumdule[enumdule["Red"] = 0] = "Red";
enumdule[enumdule["Blue"] = 1] = "Blue";
@@ -50,7 +50,6 @@ var A;
}());
A.Point = Point;
})(A || (A = {}));
var A;
(function (A) {
var Point = (function () {
function Point() {
@@ -79,7 +78,6 @@ var X;
})(Z = Y.Z || (Y.Z = {}));
})(Y = X.Y || (X.Y = {}));
})(X || (X = {}));
var X;
(function (X) {
var Y;
(function (Y) {
@@ -42,7 +42,6 @@ var A;
}());
A.Point = Point;
})(A || (A = {}));
var A;
(function (A) {
// expected error
var Point = (function () {
@@ -67,7 +66,6 @@ var X;
})(Z = Y.Z || (Y.Z = {}));
})(Y = X.Y || (X.Y = {}));
})(X || (X = {}));
var X;
(function (X) {
var Y;
(function (Y) {
@@ -41,7 +41,6 @@ var A;
(function (B) {
})(B = A.B || (A.B = {}));
})(A || (A = {}));
var A;
(function (A) {
var B;
(function (B) {
@@ -65,7 +64,6 @@ var X;
})(Z = Y.Z || (Y.Z = {}));
})(Y = X.Y || (X.Y = {}));
})(X || (X = {}));
var X;
(function (X) {
var Y;
(function (Y) {
@@ -22,7 +22,7 @@ var __extends = (this && this.__extends) || function (d, b) {
var B = (function (_super) {
__extends(B, _super);
function B() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return B;
}(A));
@@ -22,7 +22,7 @@ var __extends = (this && this.__extends) || function (d, b) {
var B = (function (_super) {
__extends(B, _super);
function B() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return B;
}(A));
@@ -35,9 +35,10 @@ var B = (function () {
var C = (function (_super) {
__extends(C, _super);
function C() {
_super.apply(this, arguments);
this.raw = "edge";
this.ro = "readonly please";
var _this = _super.apply(this, arguments) || this;
_this.raw = "edge";
_this.ro = "readonly please";
return _this;
}
Object.defineProperty(C.prototype, "prop", {
get: function () { return "foo"; },
@@ -57,8 +57,9 @@ var B = (function () {
var C = (function (_super) {
__extends(C, _super);
function C() {
_super.apply(this, arguments);
this.ro = "readonly please";
var _this = _super.apply(this, arguments) || this;
_this.ro = "readonly please";
return _this;
}
Object.defineProperty(C.prototype, "concreteWithNoBody", {
get: function () { },
@@ -77,8 +78,9 @@ var WrongTypeProperty = (function () {
var WrongTypePropertyImpl = (function (_super) {
__extends(WrongTypePropertyImpl, _super);
function WrongTypePropertyImpl() {
_super.apply(this, arguments);
this.num = "nope, wrong";
var _this = _super.apply(this, arguments) || this;
_this.num = "nope, wrong";
return _this;
}
return WrongTypePropertyImpl;
}(WrongTypeProperty));
@@ -90,7 +92,7 @@ var WrongTypeAccessor = (function () {
var WrongTypeAccessorImpl = (function (_super) {
__extends(WrongTypeAccessorImpl, _super);
function WrongTypeAccessorImpl() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
Object.defineProperty(WrongTypeAccessorImpl.prototype, "num", {
get: function () { return "nope, wrong"; },
@@ -102,8 +104,9 @@ var WrongTypeAccessorImpl = (function (_super) {
var WrongTypeAccessorImpl2 = (function (_super) {
__extends(WrongTypeAccessorImpl2, _super);
function WrongTypeAccessorImpl2() {
_super.apply(this, arguments);
this.num = "nope, wrong";
var _this = _super.apply(this, arguments) || this;
_this.num = "nope, wrong";
return _this;
}
return WrongTypeAccessorImpl2;
}(WrongTypeAccessor));
@@ -34,8 +34,9 @@ var Point = (function () {
var ColoredPoint = (function (_super) {
__extends(ColoredPoint, _super);
function ColoredPoint(x, y, color) {
_super.call(this, x, y);
this.color = color;
var _this = _super.call(this, x, y) || this;
_this.color = color;
return _this;
}
ColoredPoint.prototype.toString = function () {
return _super.prototype.toString.call(this) + " color=" + this.color;
@@ -38,7 +38,7 @@ var A = (function () {
var B = (function (_super) {
__extends(B, _super);
function B() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return B;
}(A));
@@ -46,7 +46,7 @@ var Backbone = require("./aliasUsage1_backbone");
var VisualizationModel = (function (_super) {
__extends(VisualizationModel, _super);
function VisualizationModel() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return VisualizationModel;
}(Backbone.Model));
@@ -40,7 +40,7 @@ var Backbone = require("./aliasUsageInArray_backbone");
var VisualizationModel = (function (_super) {
__extends(VisualizationModel, _super);
function VisualizationModel() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return VisualizationModel;
}(Backbone.Model));
@@ -39,7 +39,7 @@ var Backbone = require("./aliasUsageInFunctionExpression_backbone");
var VisualizationModel = (function (_super) {
__extends(VisualizationModel, _super);
function VisualizationModel() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return VisualizationModel;
}(Backbone.Model));
@@ -43,7 +43,7 @@ var Backbone = require("./aliasUsageInGenericFunction_backbone");
var VisualizationModel = (function (_super) {
__extends(VisualizationModel, _super);
function VisualizationModel() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return VisualizationModel;
}(Backbone.Model));
@@ -45,7 +45,7 @@ var Backbone = require("./aliasUsageInIndexerOfClass_backbone");
var VisualizationModel = (function (_super) {
__extends(VisualizationModel, _super);
function VisualizationModel() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return VisualizationModel;
}(Backbone.Model));
@@ -40,7 +40,7 @@ var Backbone = require("./aliasUsageInObjectLiteral_backbone");
var VisualizationModel = (function (_super) {
__extends(VisualizationModel, _super);
function VisualizationModel() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return VisualizationModel;
}(Backbone.Model));
@@ -43,7 +43,7 @@ var Backbone = require("./aliasUsageInOrExpression_backbone");
var VisualizationModel = (function (_super) {
__extends(VisualizationModel, _super);
function VisualizationModel() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return VisualizationModel;
}(Backbone.Model));
@@ -43,7 +43,7 @@ var Backbone = require("./aliasUsageInTypeArgumentOfExtendsClause_backbone");
var VisualizationModel = (function (_super) {
__extends(VisualizationModel, _super);
function VisualizationModel() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return VisualizationModel;
}(Backbone.Model));
@@ -64,8 +64,9 @@ var C = (function () {
var D = (function (_super) {
__extends(D, _super);
function D() {
_super.apply(this, arguments);
this.x = moduleA;
var _this = _super.apply(this, arguments) || this;
_this.x = moduleA;
return _this;
}
return D;
}(C));
@@ -39,7 +39,7 @@ var Backbone = require("./aliasUsageInVarAssignment_backbone");
var VisualizationModel = (function (_super) {
__extends(VisualizationModel, _super);
function VisualizationModel() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return VisualizationModel;
}(Backbone.Model));
@@ -22,7 +22,7 @@ var A = (function () {
var B = (function (_super) {
__extends(B, _super);
function B() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return B;
}(A));
@@ -119,7 +119,6 @@ var E;
})(E || (E = {}));
var r3 = foo3(a); // any
function f() { }
var f;
(function (f) {
f.bar = 1;
})(f || (f = {}));
@@ -129,7 +128,6 @@ var CC = (function () {
}
return CC;
}());
var CC;
(function (CC) {
CC.bar = 1;
})(CC || (CC = {}));
@@ -147,7 +147,6 @@ var E;
E[E["A"] = 0] = "A";
})(E || (E = {}));
function f() { }
var f;
(function (f) {
f.bar = 1;
})(f || (f = {}));
@@ -156,7 +155,6 @@ var c = (function () {
}
return c;
}());
var c;
(function (c) {
c.bar = 1;
})(c || (c = {}));
@@ -38,7 +38,7 @@ var Base = (function () {
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
@@ -51,7 +51,7 @@ var Base2 = (function () {
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Base2));
@@ -28,7 +28,7 @@ var Base = (function () {
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
@@ -101,7 +101,7 @@ var C1 = (function () {
var C2 = (function (_super) {
__extends(C2, _super);
function C2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
C2.prototype.C2M1 = function () { return null; };
return C2;
@@ -75,7 +75,7 @@ var C1 = (function () {
var C2 = (function (_super) {
__extends(C2, _super);
function C2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
C2.prototype.C2M1 = function () { return null; };
return C2;
@@ -128,7 +128,7 @@ var EmptyTypes;
var derived = (function (_super) {
__extends(derived, _super);
function derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return derived;
}(base));
@@ -187,7 +187,7 @@ var NonEmptyTypes;
var derived = (function (_super) {
__extends(derived, _super);
function derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return derived;
}(base));
@@ -65,14 +65,14 @@ var Action = (function () {
var ActionA = (function (_super) {
__extends(ActionA, _super);
function ActionA() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return ActionA;
}(Action));
var ActionB = (function (_super) {
__extends(ActionB, _super);
function ActionB() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return ActionB;
}(Action));
+2 -2
View File
@@ -70,7 +70,7 @@ var Base = (function () {
var Derived1 = (function (_super) {
__extends(Derived1, _super);
function Derived1() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived1;
}(Base));
@@ -78,7 +78,7 @@ var Derived1 = (function (_super) {
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Base));
@@ -39,7 +39,7 @@ var List = (function () {
var DerivedList = (function (_super) {
__extends(DerivedList, _super);
function DerivedList() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return DerivedList;
}(List));
@@ -33,14 +33,14 @@ var A = (function () {
var B = (function (_super) {
__extends(B, _super);
function B() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return B;
}(A));
var C = (function (_super) {
__extends(C, _super);
function C() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return C;
}(Array));
@@ -116,8 +116,7 @@ var Base = (function () {
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
var _this = this;
_super.call(this, function () { return _this; });
return _super.call(this, function () { return _this; }) || this;
}
return Derived;
}(Base));
@@ -158,8 +157,7 @@ var M2;
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
var _this = this;
_super.call(this, function () { return _this; });
return _super.call(this, function () { return _this; }) || this;
}
return Derived;
}(Base));
@@ -114,21 +114,21 @@ var Base = (function () {
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Derived));
var OtherDerived = (function (_super) {
__extends(OtherDerived, _super);
function OtherDerived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return OtherDerived;
}(Base));
@@ -115,21 +115,21 @@ var Errors;
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Derived));
var OtherDerived = (function (_super) {
__extends(OtherDerived, _super);
function OtherDerived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return OtherDerived;
}(Base));
@@ -80,21 +80,21 @@ var Base = (function () {
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Derived));
var OtherDerived = (function (_super) {
__extends(OtherDerived, _super);
function OtherDerived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return OtherDerived;
}(Base));
@@ -57,21 +57,21 @@ var Base = (function () {
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Derived));
var OtherDerived = (function (_super) {
__extends(OtherDerived, _super);
function OtherDerived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return OtherDerived;
}(Base));
@@ -114,21 +114,21 @@ var Base = (function () {
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Derived));
var OtherDerived = (function (_super) {
__extends(OtherDerived, _super);
function OtherDerived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return OtherDerived;
}(Base));
@@ -115,21 +115,21 @@ var Errors;
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Derived));
var OtherDerived = (function (_super) {
__extends(OtherDerived, _super);
function OtherDerived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return OtherDerived;
}(Base));
@@ -80,21 +80,21 @@ var Base = (function () {
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Derived));
var OtherDerived = (function (_super) {
__extends(OtherDerived, _super);
function OtherDerived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return OtherDerived;
}(Base));
@@ -57,21 +57,21 @@ var Base = (function () {
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Derived));
var OtherDerived = (function (_super) {
__extends(OtherDerived, _super);
function OtherDerived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return OtherDerived;
}(Base));
@@ -72,7 +72,7 @@ var Generics;
var B = (function (_super) {
__extends(B, _super);
function B() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return B;
}(A));
@@ -59,7 +59,7 @@ b = a; // ok
var B2 = (function (_super) {
__extends(B2, _super);
function B2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return B2;
}(A));
@@ -108,14 +108,14 @@ var OnlyDerived;
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Base));
@@ -167,14 +167,14 @@ var WithBase;
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Base));
@@ -157,7 +157,6 @@ var TargetIsPublic;
e = d; // errror
e = e;
})(TargetIsPublic || (TargetIsPublic = {}));
var TargetIsPublic;
(function (TargetIsPublic) {
// targets
var Base = (function () {
@@ -103,14 +103,14 @@ var Base = (function () {
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Derived));
@@ -105,14 +105,14 @@ var Base = (function () {
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived;
}(Base));
var Derived2 = (function (_super) {
__extends(Derived2, _super);
function Derived2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Derived2;
}(Derived));
@@ -82,7 +82,7 @@ var Generics;
var B = (function (_super) {
__extends(B, _super);
function B() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return B;
}(A));
@@ -93,7 +93,7 @@ var Generics;
var B2 = (function (_super) {
__extends(B2, _super);
function B2() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return B2;
}(A));
@@ -118,8 +118,9 @@ value;
var Derived = (function (_super) {
__extends(Derived, _super);
function Derived() {
_super.call(this);
var _this = _super.call(this) || this;
_super.prototype. = value;
return _this;
}
Derived.prototype.foo = function () { _super.prototype. = value; };
Derived.sfoo = function () { _super. = value; };
@@ -38,20 +38,17 @@ var goodObj = {
}; // Ok, because toString is a subtype of Object's toString
var errFun = {}; // Error for no call signature
function foo() { }
var foo;
(function (foo) {
foo.boom = 0;
})(foo || (foo = {}));
var goodFundule = foo; // ok
function bar() { }
var bar;
(function (bar) {
function apply(thisArg, argArray) { }
bar.apply = apply;
})(bar || (bar = {}));
var goodFundule2 = bar; // ok
function bad() { }
var bad;
(function (bad) {
bad.apply = 0;
})(bad || (bad = {}));
@@ -19,7 +19,7 @@ var __extends = (this && this.__extends) || function (d, b) {
var Task = (function (_super) {
__extends(Task, _super);
function Task() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return Task;
}(Promise));
@@ -61,7 +61,7 @@ var A = (function () {
var B = (function (_super) {
__extends(B, _super);
function B() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
// async method with only call/get on 'super' does not require a binding
B.prototype.simple = function () {
@@ -13,7 +13,7 @@ var X;
var MyPromise = (function (_super) {
__extends(MyPromise, _super);
function MyPromise() {
_super.apply(this, arguments);
return _super.apply(this, arguments) || this;
}
return MyPromise;
}(Promise));
@@ -28,7 +28,6 @@ let b = x.b;
define(["require", "exports"], function (require, exports) {
"use strict";
function foo() { }
var foo;
(function (foo) {
foo.v = 1;
})(foo || (foo = {}));
@@ -32,7 +32,6 @@ define(["require", "exports"], function (require, exports) {
}
return foo;
}());
var foo;
(function (foo) {
foo.v = 1;
})(foo || (foo = {}));
@@ -36,7 +36,6 @@ define(["require", "exports"], function (require, exports) {
}
return foo;
}());
var foo;
(function (foo) {
var A = (function () {
function A() {
@@ -23,7 +23,6 @@ var c4 = (function () {
c4.prototype.foo = function () { };
return c4;
}());
var c4;
(function (c4) {
c4[c4["One"] = 0] = "One";
})(c4 || (c4 = {})); // error
@@ -51,7 +51,6 @@ var c33 = (function () {
};
return c33;
}());
var c33;
(function (c33) {
c33[c33["One"] = 0] = "One";
})(c33 || (c33 = {}));
@@ -27,7 +27,6 @@ var c5a = (function () {
c5a.prototype.foo = function () { };
return c5a;
}());
var c5a;
(function (c5a) {
var y = 2;
})(c5a || (c5a = {})); // should be ok
@@ -37,7 +36,6 @@ var c5b = (function () {
c5b.prototype.foo = function () { };
return c5b;
}());
var c5b;
(function (c5b) {
c5b.y = 2;
})(c5b || (c5b = {})); // should be ok
@@ -69,7 +69,6 @@ var e5;
(function (e5) {
e5[e5["One"] = 0] = "One";
})(e5 || (e5 = {}));
var e5;
(function (e5) {
e5[e5["Two"] = 0] = "Two";
})(e5 || (e5 = {})); // error
@@ -77,7 +76,6 @@ var e5a;
(function (e5a) {
e5a[e5a["One"] = 0] = "One";
})(e5a || (e5a = {})); // error
var e5a;
(function (e5a) {
e5a[e5a["One"] = 0] = "One";
})(e5a || (e5a = {})); // error
@@ -90,7 +88,6 @@ var e6a;
(function (e6a) {
e6a[e6a["One"] = 0] = "One";
})(e6a || (e6a = {}));
var e6a;
(function (e6a) {
var y = 2;
})(e6a || (e6a = {})); // should be error
@@ -98,7 +95,6 @@ var e6b;
(function (e6b) {
e6b[e6b["One"] = 0] = "One";
})(e6b || (e6b = {}));
var e6b;
(function (e6b) {
e6b.y = 2;
})(e6b || (e6b = {})); // should be error
@@ -25,13 +25,11 @@ var E;
(function (E) {
var t;
})(E || (E = {}));
var E;
(function (E) {
})(E || (E = {}));
var F;
(function (F) {
})(F || (F = {}));
var F;
(function (F) {
var t;
})(F || (F = {}));
@@ -39,15 +37,12 @@ var A;
(function (A) {
var o;
})(A || (A = {}));
var A;
(function (A) {
A[A["b"] = 0] = "b";
})(A || (A = {}));
var A;
(function (A) {
A[A["c"] = 0] = "c";
})(A || (A = {}));
var A;
(function (A) {
var p;
})(A || (A = {}));
@@ -63,19 +63,16 @@ var y3a = (function () {
}()); // error
// function then enum
function y4() { } // error
var y4;
(function (y4) {
y4[y4["One"] = 0] = "One";
})(y4 || (y4 = {})); // error
// function then internal module
function y5() { }
function y5a() { }
var y5a;
(function (y5a) {
var y = 2;
})(y5a || (y5a = {})); // should be an error
function y5b() { }
var y5b;
(function (y5b) {
y5b.y = 3;
})(y5b || (y5b = {})); // should be an error
@@ -138,7 +138,6 @@ function m2b() { }
// should be errors to have function first
function m2c() { }
;
var m2c;
(function (m2c) {
m2c.y = 2;
})(m2c || (m2c = {}));
@@ -146,7 +145,6 @@ function m2f() { }
;
function m2g() { }
;
var m2g;
(function (m2g) {
var C = (function () {
function C() {
@@ -177,7 +175,6 @@ var m3b = (function () {
m3b.prototype.foo = function () { };
return m3b;
}());
var m3b;
(function (m3b) {
var y = 2;
})(m3b || (m3b = {}));
@@ -187,7 +184,6 @@ var m3c = (function () {
m3c.prototype.foo = function () { };
return m3c;
}());
var m3c;
(function (m3c) {
m3c.y = 2;
})(m3c || (m3c = {}));
@@ -216,7 +212,6 @@ var m4a;
(function (m4a) {
var y = 2;
})(m4a || (m4a = {}));
var m4a;
(function (m4a) {
m4a[m4a["One"] = 0] = "One";
})(m4a || (m4a = {}));
@@ -224,7 +219,6 @@ var m4b;
(function (m4b) {
m4b.y = 2;
})(m4b || (m4b = {}));
var m4b;
(function (m4b) {
m4b[m4b["One"] = 0] = "One";
})(m4b || (m4b = {}));
@@ -241,7 +235,6 @@ var m4d;
return C;
}());
})(m4d || (m4d = {}));
var m4d;
(function (m4d) {
m4d[m4d["One"] = 0] = "One";
})(m4d || (m4d = {}));
@@ -45,7 +45,6 @@ function m2b() { }
; // error since the module is instantiated
function m2c() { }
;
var m2c;
(function (m2c) {
m2c.y = 2;
})(m2c || (m2c = {}));
@@ -59,7 +58,6 @@ function m2f() { }
;
function m2g() { }
;
var m2g;
(function (m2g) {
var C = (function () {
function C() {
@@ -25,7 +25,6 @@ var m3b = (function () {
m3b.prototype.foo = function () { };
return m3b;
}());
var m3b;
(function (m3b) {
var y = 2;
})(m3b || (m3b = {}));
@@ -35,7 +34,6 @@ var m3c = (function () {
m3c.prototype.foo = function () { };
return m3c;
}());
var m3c;
(function (m3c) {
m3c.y = 2;
})(m3c || (m3c = {}));

Some files were not shown because too many files have changed in this diff Show More