1

查看了declarationEmitter和變量聲明,它具有函數#emitVariableDeclaration,最終調用#writeTypeOfDeclaration。這段代碼沒有做什麼說---它需要一個變量聲明並打印變量及其類型---這正是我想要做的。在打字稿AST中爲變量聲明獲取類型的正確方法?

問題是,當我複製此代碼時,VariableDeclaration節點沒有符號屬性...因此,類型始終爲「任何」。 初始化「符號」是否存在缺失步驟?

//sample input filecontents 
export const foo = '123' 

//mycode.js 
const ast = ts.createSourceFile(filename, filecontents, ts.ScriptTarget.ES6, true)) 
const program = ts.createProgram([filename], {}); 
const typeChecker = program.getDiagnosticsProducingTypeChecker() 
const emitResolver = typeChecker.getEmitResolver(filename) 
// variableDeclarationNode --- can be obtained using ts.forEachChild and finding node with kind === ts.SyntaxKind.VariableDeclaration 
// writer --- an object implementing the SymbolWriter interface that just concatenates to a result string 
emitResolver.writeTypeOfDeclaration(variableDeclarationNode, undefined, undefined, writer) 

//declarationEmitter.ts 
function writeTypeOfDeclaration(
     declaration: AccessorDeclaration | VariableLikeDeclaration, 
     type: TypeNode, 
     getSymbolAccessibilityDiagnostic: GetSymbolAccessibilityDiagnostic) { 
    //... 
    resolver.writeTypeOfDeclaration(declaration, enclosingDeclaration, TypeFormatFlags.UseTypeOfFunction, writer); 
} 

//`checker.ts` 
function writeTypeOfDeclaration(
    declaration: AccessorDeclaration | VariableLikeDeclaration,  
    enclosingDeclaration: Node, 
    flags: TypeFormatFlags, 
    writer: SymbolWriter) { 

    // Get type of the symbol if this is the valid symbol otherwise get type at location 
    const symbol = getSymbolOfNode(declaration); 
    const type = symbol && !(symbol.flags & (SymbolFlags.TypeLiteral | SymbolFlags.Signature)) 
     ? getTypeOfSymbol(symbol) 
     : unknownType; 

    // .... 
} 

function getMergedSymbol(symbol: Symbol): Symbol { 
    let merged: Symbol; 
    return symbol && symbol.mergeId && (merged = mergedSymbols[symbol.mergeId]) ? merged : symbol; 
} 

function getSymbolOfNode(node: Node): Symbol { 
    return getMergedSymbol(node.symbol); 
} 

回答

0

原來我用錯了AST。在問題中,我使用的是沒有類型的AST。您可以使用該程序注入類型爲AST的AST。 (更多)正確的解決方案是:

const program = ts.createProgram(filename, {target: ts.ScriptTarget.ES6, module: ts.ModuleKind.ES6}); 
const typechecker = program.getDiagnosticsProducingTypeChecker() 
const emitResolver = typeChecker.getEmitResolver(filename))) 

// THIS IS HOW TO GET AN AST WITH TYPE (Yes, it's called a "SourceFile") 
const ast = program.getSourceFile(filename) 

// variableDeclarationNode --- can be obtained using ts.forEachChild and finding node with kind === ts.SyntaxKind.VariableDeclaration 
// writer --- an object implementing the SymbolWriter interface that just concatenates to a result string 
emitResolver.writeTypeOfDeclaration(variableDeclarationNode, undefined, undefined, writer) 
+0

是的。您需要使用該程序:) – basarat

+0

'getEmitResolver'是一個內部API。有沒有公​​共的API可以使用? – Josh

相關問題