diff --git a/src/compiler/binder.ts b/src/compiler/binder.ts index 1502dbc8ead..a0fd0b243d6 100644 --- a/src/compiler/binder.ts +++ b/src/compiler/binder.ts @@ -66,9 +66,9 @@ module ts { export function bindSourceFile(file: SourceFile) { var parent: Node; - var container: Declaration; + var container: Node; var blockScopeContainer: Node; - var lastContainer: Declaration; + var lastContainer: Node; var symbolCount = 0; var Symbol = objectAllocator.getSymbolConstructor(); @@ -222,7 +222,7 @@ module ts { // All container nodes are kept on a linked list in declaration order. This list is used by the getLocalNameOfContainer function // in the type checker to validate that the local name used for a container is unique. - function bindChildren(node: Declaration, symbolKind: SymbolFlags, isBlockScopeContainer: boolean) { + function bindChildren(node: Node, symbolKind: SymbolFlags, isBlockScopeContainer: boolean) { if (symbolKind & SymbolFlags.HasLocals) { node.locals = {}; } @@ -341,7 +341,7 @@ module ts { typeLiteralSymbol.members[node.kind === SyntaxKind.FunctionType ? "__call" : "__new"] = symbol } - function bindAnonymousDeclaration(node: Node, symbolKind: SymbolFlags, name: string, isBlockScopeContainer: boolean) { + function bindAnonymousDeclaration(node: Declaration, symbolKind: SymbolFlags, name: string, isBlockScopeContainer: boolean) { var symbol = createSymbol(symbolKind, name); addDeclarationToSymbol(symbol, node, symbolKind); bindChildren(node, symbolKind, isBlockScopeContainer); @@ -434,14 +434,14 @@ module ts { break; case SyntaxKind.TypeLiteral: - bindAnonymousDeclaration(node, SymbolFlags.TypeLiteral, "__type", /*isBlockScopeContainer*/ false); + bindAnonymousDeclaration(node, SymbolFlags.TypeLiteral, "__type", /*isBlockScopeContainer*/ false); break; case SyntaxKind.ObjectLiteralExpression: - bindAnonymousDeclaration(node, SymbolFlags.ObjectLiteral, "__object", /*isBlockScopeContainer*/ false); + bindAnonymousDeclaration(node, SymbolFlags.ObjectLiteral, "__object", /*isBlockScopeContainer*/ false); break; case SyntaxKind.FunctionExpression: case SyntaxKind.ArrowFunction: - bindAnonymousDeclaration(node, SymbolFlags.Function, "__function", /*isBlockScopeContainer*/ true); + bindAnonymousDeclaration(node, SymbolFlags.Function, "__function", /*isBlockScopeContainer*/ true); break; case SyntaxKind.CatchBlock: bindCatchVariableDeclaration(node); @@ -471,7 +471,7 @@ module ts { break; case SyntaxKind.SourceFile: if (isExternalModule(node)) { - bindAnonymousDeclaration(node, SymbolFlags.ValueModule, '"' + removeFileExtension((node).filename) + '"', /*isBlockScopeContainer*/ true); + bindAnonymousDeclaration(node, SymbolFlags.ValueModule, '"' + removeFileExtension((node).filename) + '"', /*isBlockScopeContainer*/ true); break; } diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 2d9f7b44fb9..52014289ad1 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -935,7 +935,7 @@ module ts { return { accessibility: SymbolAccessibility.Accessible }; - function getExternalModuleContainer(declaration: Declaration) { + function getExternalModuleContainer(declaration: Node) { for (; declaration; declaration = declaration.parent) { if (hasExternalModuleSymbol(declaration)) { return getSymbolOfNode(declaration); @@ -944,8 +944,8 @@ module ts { } } - function hasExternalModuleSymbol(declaration: Declaration) { - return (declaration.kind === SyntaxKind.ModuleDeclaration && declaration.name.kind === SyntaxKind.StringLiteral) || + function hasExternalModuleSymbol(declaration: Node) { + return (declaration.kind === SyntaxKind.ModuleDeclaration && (declaration).name.kind === SyntaxKind.StringLiteral) || (declaration.kind === SyntaxKind.SourceFile && isExternalModule(declaration)); } @@ -962,7 +962,7 @@ module ts { // because these kind of aliases can be used to name types in declaration file if (declaration.kind === SyntaxKind.ImportDeclaration && !(declaration.flags & NodeFlags.Export) && - isDeclarationVisible(declaration.parent)) { + isDeclarationVisible(declaration.parent)) { getNodeLinks(declaration).isVisible = true; if (aliasesToMakeVisible) { if (!contains(aliasesToMakeVisible, declaration)) { @@ -1575,7 +1575,7 @@ module ts { } // Container of resolvedExportSymbol is visible - return forEach(resolvedExportSymbol.declarations, declaration => { + return forEach(resolvedExportSymbol.declarations, (declaration: Node) => { while (declaration) { if (declaration === node) { return true; @@ -1605,7 +1605,7 @@ module ts { return isGlobalSourceFile(parent) || isUsedInExportAssignment(node); } // Exported members/ambient module elements (exception import declaration) are visible if parent is visible - return isDeclarationVisible(parent); + return isDeclarationVisible(parent); case SyntaxKind.Property: case SyntaxKind.Method: @@ -1622,7 +1622,7 @@ module ts { case SyntaxKind.Parameter: case SyntaxKind.ModuleBlock: case SyntaxKind.TypeParameter: - return isDeclarationVisible(node.parent); + return isDeclarationVisible(node.parent); // Source file is always visible case SyntaxKind.SourceFile: diff --git a/src/compiler/emitter.ts b/src/compiler/emitter.ts index b81c16cad90..9d9852d8bda 100644 --- a/src/compiler/emitter.ts +++ b/src/compiler/emitter.ts @@ -357,7 +357,7 @@ module ts { var currentSourceFile: SourceFile; var reportedDeclarationError = false; - var emitJsDocComments = compilerOptions.removeComments ? function (declaration: Declaration) { } : writeJsDocComments; + var emitJsDocComments = compilerOptions.removeComments ? function (declaration: Node) { } : writeJsDocComments; var aliasDeclarationEmitInfo: AliasDeclarationEmitInfo[] = []; @@ -485,7 +485,7 @@ module ts { emitSeparatedList(nodes, ", ", eachNodeEmitFn); } - function writeJsDocComments(declaration: Declaration) { + function writeJsDocComments(declaration: Node) { if (declaration) { var jsDocComments = getJsDocComments(declaration, currentSourceFile); emitNewLineBeforeLeadingComments(currentSourceFile, writer, declaration, jsDocComments); @@ -615,7 +615,7 @@ module ts { writeLine(); } - function emitModuleElementDeclarationFlags(node: Declaration) { + function emitModuleElementDeclarationFlags(node: Node) { // If the node is parented in the current source file we need to emit export declare or just export if (node.parent === currentSourceFile) { // If the node is exported diff --git a/src/compiler/parser.ts b/src/compiler/parser.ts index 1c7f7035759..211ac1e7470 100644 --- a/src/compiler/parser.ts +++ b/src/compiler/parser.ts @@ -126,15 +126,15 @@ module ts { return (file.flags & NodeFlags.DeclarationFile) !== 0; } - export function isConstEnumDeclaration(node: Declaration): boolean { + export function isConstEnumDeclaration(node: Node): boolean { return node.kind === SyntaxKind.EnumDeclaration && isConst(node); } - export function isConst(node: Declaration): boolean { + export function isConst(node: Node): boolean { return !!(node.flags & NodeFlags.Const); } - export function isLet(node: Declaration): boolean { + export function isLet(node: Node): boolean { return !!(node.flags & NodeFlags.Let); } @@ -171,8 +171,8 @@ module ts { } } - export function getJsDocComments(node: Declaration, sourceFileOfNode: SourceFile) { - return filter(getLeadingCommentRangesOfNode(node, sourceFileOfNode), comment => isJsDocComment(comment)); + export function getJsDocComments(node: Node, sourceFileOfNode: SourceFile) { + return filter(getLeadingCommentRangesOfNode(node, sourceFileOfNode), isJsDocComment); function isJsDocComment(comment: CommentRange) { // True if the comment starts with '/**' but not if it is '/**/' @@ -1988,7 +1988,7 @@ module ts { parseExpected(SyntaxKind.CloseBraceToken); } else { - members = createMissingList(); + members = createMissingList(); } return members; @@ -3084,7 +3084,7 @@ module ts { return finishNode(node); } - function parseObjectLiteralMember(): Node { + function parseObjectLiteralMember(): Declaration { var initialPos = getNodePos(); var initialToken = token; if (parseContextualModifier(SyntaxKind.GetKeyword) || parseContextualModifier(SyntaxKind.SetKeyword)) { diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 9a1b2095bc9..093e27f32e7 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -336,6 +336,7 @@ module ts { export type DeclarationName = Identifier | LiteralExpression | ComputedPropertyName; export interface Declaration extends Node { + _declarationBrand: any; name?: DeclarationName; } @@ -392,7 +393,7 @@ module ts { body?: Block; } - export interface ConstructorDeclaration extends Node, ParsedSignature { + export interface ConstructorDeclaration extends Declaration, ParsedSignature { body?: Block; } @@ -411,7 +412,7 @@ module ts { exprName: EntityName; } - export interface TypeLiteralNode extends TypeNode { + export interface TypeLiteralNode extends TypeNode, Declaration { members: NodeArray; } @@ -538,8 +539,8 @@ module ts { elements: NodeArray; } - export interface ObjectLiteralExpression extends PrimaryExpression { - properties: NodeArray; + export interface ObjectLiteralExpression extends PrimaryExpression, Declaration { + properties: NodeArray; } export interface PropertyAccessExpression extends MemberExpression { @@ -659,7 +660,7 @@ module ts { finallyBlock?: Block; } - export interface CatchBlock extends Block { + export interface CatchBlock extends Block, Declaration { variable: Identifier; type?: TypeNode; } @@ -673,14 +674,14 @@ module ts { typeParameters?: NodeArray; baseType?: TypeReferenceNode; implementedTypes?: NodeArray; - members: NodeArray; + members: NodeArray; } export interface InterfaceDeclaration extends Declaration, ModuleElement { name: Identifier; typeParameters?: NodeArray; baseTypes?: NodeArray; - members: NodeArray; + members: NodeArray; } export interface TypeAliasDeclaration extends Declaration, ModuleElement { @@ -727,7 +728,8 @@ module ts { hasTrailingNewLine?: boolean; } - export interface SourceFile extends Node { + // Source files are declarations when they are external modules. + export interface SourceFile extends Declaration { statements: NodeArray; filename: string; diff --git a/src/services/services.ts b/src/services/services.ts index 33212de3988..6386a472600 100644 --- a/src/services/services.ts +++ b/src/services/services.ts @@ -349,7 +349,7 @@ module ts { // If this is dotted module name, get the doc comments from the parent while (declaration.kind === SyntaxKind.ModuleDeclaration && declaration.parent.kind === SyntaxKind.ModuleDeclaration) { - declaration = declaration.parent; + declaration = declaration.parent; } // Get the cleaned js doc comment text from the declaration @@ -712,6 +712,7 @@ module ts { } class SourceFileObject extends NodeObject implements SourceFile { + public _declarationBrand: any; public filename: string; public text: string; @@ -771,7 +772,7 @@ module ts { } } else { - namedDeclarations.push(node); + namedDeclarations.push(functionDeclaration); } forEachChild(node, visit); @@ -3798,7 +3799,7 @@ module ts { } } - function getModifierOccurrences(modifier: SyntaxKind, declaration: Declaration) { + function getModifierOccurrences(modifier: SyntaxKind, declaration: Node) { var container = declaration.parent; // Make sure we only highlight the keyword when it makes sense to do so. @@ -4739,7 +4740,7 @@ module ts { return emitOutput; } - function getMeaningFromDeclaration(node: Declaration): SemanticMeaning { + function getMeaningFromDeclaration(node: Node): SemanticMeaning { switch (node.kind) { case SyntaxKind.Parameter: case SyntaxKind.VariableDeclaration: