Skip to content

Commit

Permalink
Refactor declaration emitter into declaration transformer (#21930)
Browse files Browse the repository at this point in the history
* Refactor declaration emitter into declaration transformer

* Slight cleanup from code review feedback

* Incorporate fix for new test

* Swaths of PR feedback

* Merge public methods

* Per-file output

* Preserve input import ordering more often

* Unify jsdoc comment start detection under more lenient rule

* Move to per-file transformations to reduce the memory that msut be retained

* Fix typo
  • Loading branch information
weswigham authored Mar 16, 2018
1 parent 162a273 commit 19ec83f
Show file tree
Hide file tree
Showing 124 changed files with 2,656 additions and 2,729 deletions.
51 changes: 32 additions & 19 deletions src/compiler/checker.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3684,10 +3684,6 @@ namespace ts {
isExternalModuleAugmentation(node.parent.parent);
}

function literalTypeToString(type: LiteralType) {
return type.flags & TypeFlags.StringLiteral ? '"' + escapeString((<StringLiteralType>type).value) + '"' : "" + (<NumberLiteralType>type).value;
}

interface NodeBuilderContext {
enclosingDeclaration: Node | undefined;
flags: NodeBuilderFlags | undefined;
Expand Down Expand Up @@ -3748,7 +3744,7 @@ namespace ts {
return symbolName(symbol);
}

function isDeclarationVisible(node: Declaration): boolean {
function isDeclarationVisible(node: Declaration | AnyImportSyntax): boolean {
if (node) {
const links = getNodeLinks(node);
if (links.isVisible === undefined) {
Expand Down Expand Up @@ -25497,6 +25493,7 @@ namespace ts {

function isImplementationOfOverload(node: SignatureDeclaration) {
if (nodeIsPresent((node as FunctionLikeDeclaration).body)) {
if (isGetAccessor(node) || isSetAccessor(node)) return false; // Get or set accessors can never be overload implementations, but can have up to 2 signatures
const symbol = getSymbolOfNode(node);
const signaturesOfSymbol = getSignaturesOfSymbol(symbol);
// If this function body corresponds to function with multiple signature, it is implementation of overload
Expand Down Expand Up @@ -25636,30 +25633,42 @@ namespace ts {
}
}

function writeTypeOfDeclaration(declaration: AccessorDeclaration | VariableLikeDeclaration, enclosingDeclaration: Node, flags: TypeFormatFlags, writer: EmitTextWriter) {
function createTypeOfDeclaration(declaration: AccessorDeclaration | VariableLikeDeclaration, enclosingDeclaration: Node, flags: NodeBuilderFlags, tracker: SymbolTracker, addUndefined?: boolean) {
declaration = getParseTreeNode(declaration, isVariableLikeOrAccessor);
if (!declaration) {
return createToken(SyntaxKind.AnyKeyword) as KeywordTypeNode;
}
// Get type of the symbol if this is the valid symbol otherwise get type at location
const symbol = getSymbolOfNode(declaration);
let type = symbol && !(symbol.flags & (SymbolFlags.TypeLiteral | SymbolFlags.Signature))
? getWidenedLiteralType(getTypeOfSymbol(symbol))
: unknownType;
if (type.flags & TypeFlags.UniqueESSymbol &&
type.symbol === symbol) {
flags |= TypeFormatFlags.AllowUniqueESSymbolType;
flags |= NodeBuilderFlags.AllowUniqueESSymbolType;
}
if (flags & TypeFormatFlags.AddUndefined) {
if (addUndefined) {
type = getOptionalType(type);
}
typeToString(type, enclosingDeclaration, flags | TypeFormatFlags.MultilineObjectLiterals, writer);
return nodeBuilder.typeToTypeNode(type, enclosingDeclaration, flags | NodeBuilderFlags.MultilineObjectLiterals, tracker);
}

function writeReturnTypeOfSignatureDeclaration(signatureDeclaration: SignatureDeclaration, enclosingDeclaration: Node, flags: TypeFormatFlags, writer: EmitTextWriter) {
function createReturnTypeOfSignatureDeclaration(signatureDeclaration: SignatureDeclaration, enclosingDeclaration: Node, flags: NodeBuilderFlags, tracker: SymbolTracker) {
signatureDeclaration = getParseTreeNode(signatureDeclaration, isFunctionLike);
if (!signatureDeclaration) {
return createToken(SyntaxKind.AnyKeyword) as KeywordTypeNode;
}
const signature = getSignatureFromDeclaration(signatureDeclaration);
typeToString(getReturnTypeOfSignature(signature), enclosingDeclaration, flags | TypeFormatFlags.MultilineObjectLiterals, writer);
return nodeBuilder.typeToTypeNode(getReturnTypeOfSignature(signature), enclosingDeclaration, flags | NodeBuilderFlags.MultilineObjectLiterals, tracker);
}

function writeTypeOfExpression(expr: Expression, enclosingDeclaration: Node, flags: TypeFormatFlags, writer: EmitTextWriter) {
function createTypeOfExpression(expr: Expression, enclosingDeclaration: Node, flags: NodeBuilderFlags, tracker: SymbolTracker) {
expr = getParseTreeNode(expr, isExpression);
if (!expr) {
return createToken(SyntaxKind.AnyKeyword) as KeywordTypeNode;
}
const type = getWidenedType(getRegularTypeOfExpression(expr));
typeToString(type, enclosingDeclaration, flags | TypeFormatFlags.MultilineObjectLiterals, writer);
return nodeBuilder.typeToTypeNode(type, enclosingDeclaration, flags | NodeBuilderFlags.MultilineObjectLiterals, tracker);
}

function hasGlobalName(name: string): boolean {
Expand Down Expand Up @@ -25707,9 +25716,13 @@ namespace ts {
return false;
}

function writeLiteralConstValue(node: VariableDeclaration | PropertyDeclaration | PropertySignature | ParameterDeclaration, writer: EmitTextWriter) {
function literalTypeToNode(type: LiteralType): Expression {
return createLiteral(type.value);
}

function createLiteralConstValue(node: VariableDeclaration | PropertyDeclaration | PropertySignature | ParameterDeclaration) {
const type = getTypeOfSymbol(getSymbolOfNode(node));
writer.writeStringLiteral(literalTypeToString(<LiteralType>type));
return literalTypeToNode(<LiteralType>type);
}

function createResolver(): EmitResolver {
Expand Down Expand Up @@ -25753,9 +25766,10 @@ namespace ts {
isImplementationOfOverload,
isRequiredInitializedParameter,
isOptionalUninitializedParameterProperty,
writeTypeOfDeclaration,
writeReturnTypeOfSignatureDeclaration,
writeTypeOfExpression,
createTypeOfDeclaration,
createReturnTypeOfSignatureDeclaration,
createTypeOfExpression,
createLiteralConstValue,
isSymbolAccessible,
isEntityNameVisible,
getConstantValue: node => {
Expand All @@ -25777,7 +25791,6 @@ namespace ts {
const symbol = node && getSymbolOfNode(node);
return !!(symbol && getCheckFlags(symbol) & CheckFlags.Late);
},
writeLiteralConstValue,
getJsxFactoryEntity: location => location ? (getJsxNamespace(location), (getSourceFileOfNode(location).localJsxFactory || _jsxFactoryEntity)) : _jsxFactoryEntity
};

Expand Down
10 changes: 10 additions & 0 deletions src/compiler/comments.ts
Original file line number Diff line number Diff line change
Expand Up @@ -260,7 +260,15 @@ namespace ts {
}
}

function shouldWriteComment(text: string, pos: number) {
if (printerOptions.onlyPrintJsDocStyle) {
return (isJSDocLikeText(text, pos) || isPinnedComment(text, pos));
}
return true;
}

function emitLeadingComment(commentPos: number, commentEnd: number, kind: SyntaxKind, hasTrailingNewLine: boolean, rangePos: number) {
if (!shouldWriteComment(currentText, commentPos)) return;
if (!hasWrittenComment) {
emitNewLineBeforeLeadingCommentOfPosition(currentLineMap, writer, rangePos, commentPos);
hasWrittenComment = true;
Expand Down Expand Up @@ -292,6 +300,7 @@ namespace ts {
}

function emitTrailingComment(commentPos: number, commentEnd: number, _kind: SyntaxKind, hasTrailingNewLine: boolean) {
if (!shouldWriteComment(currentText, commentPos)) return;
// trailing comments are emitted at space/*trailing comment1 */space/*trailing comment2*/
if (!writer.isAtStartOfLine()) {
writer.write(" ");
Expand Down Expand Up @@ -404,6 +413,7 @@ namespace ts {
}

function writeComment(text: string, lineMap: number[], writer: EmitTextWriter, commentPos: number, commentEnd: number, newLine: string) {
if (!shouldWriteComment(currentText, commentPos)) return;
if (emitPos) emitPos(commentPos);
writeCommentRange(text, lineMap, writer, commentPos, commentEnd, newLine);
if (emitPos) emitPos(commentEnd);
Expand Down
Loading

0 comments on commit 19ec83f

Please sign in to comment.