microsoft / TypeScript

TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

Home Page:https://www.typescriptlang.org

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

`getJsDocTags` does not return `@type` annotations

domoritz opened this issue · comments

I am writing a typescript to JSON schema converter and use the typescript compiler to find out the types and comments of a typescript program. I am using getJsDocTags to get annotations and would like to read the @type annotation.

TypeScript Version: 2.1.1

Code

/** @TJStype integer */
const integer: number = 1;

and

/** @type integer */
const integer: number = 1;

For the symbol integer, I am calling symbol.getJsDocTags().

Expected behavior:

I'd expect to the type jsdoc annotation. In other words, I expect the call to return [{ name: 'type', text: 'integer' }].

I understand that integer is not a valid js type but this behavior is surprising nonetheless.

Actual behavior:

It is missing. I get am empty array [].

They released TypeScript 2.2 a few days ago, is this still an issue?

There is nothing explicitly related to this specific issue on the release notes, but they made some changes related to "tooling when working with editors" as Rossenwasser said, so... maybe?

--- EDIT ---

I made a few tests and seems that getJsDocTags still skips @type keyword on TypeScript 2.1.6.

Sweet. We have to look into this for YousefED/typescript-json-schema#99. We have to make some changes to work with ts 2.2.

I think this should work. Can you provide a minimal repro?

Sure, but for starters, getJsDocTags() still exists on TS 2.2?
Is there anything similar to it or it has been removed for good?

TypeScript 2.1.6

declare namespace ts {
    interface Symbol {
        getFlags(): SymbolFlags;
        getName(): string;
        getDeclarations(): Declaration[];
        getDocumentationComment(): SymbolDisplayPart[];
        getJsDocTags(): JSDocTagInfo[];
    }
}

TypeScript 2.2.1

declare namespace ts {
    interface Symbol {
        getFlags(): SymbolFlags;
        getName(): string;
        getDeclarations(): Declaration[];
        getDocumentationComment(): SymbolDisplayPart[];
    }
}
commented

It seems that this method was removed from compiler API and then added back only to language service (see #12856).
Some related issues - #11956, #10671

Would be really great if someone could point to the alternative solution.

commented

Was this issue closed because it was fixed?

was miss labeled and auto closed.

@sandersn can you please reply to this issue with the recommended way to use the new API.

The API you want is on interface Symbol now. It gives you all the tags that Typescript doesn't handle.
I don't think there's a direct way to get the @type tag, but @TSType works. Here are my results with typescript@next:

  1. In the file test.ts put the code:
/** @TSType int */
let x: number = 12
  1. I did the following at the repl:
var ts = require('typescript')
var program = ts.createProgram(['test.ts'], {})
var checker = program.getTypeChecker()
var test_ts = program.getSourceFiles()[1]
var declName = test_ts.statements[0].declarationList.declarations[0].name
var symbol = checker.getSymbolAtLocation(declName)
var type = checker.getTypeAtLocation(declName)
var tags = symbol.getJsDocTags()
console.log(tags) // prints: [ { name: 'TSType', text: 'int ' } ]
console.log(type.intrinsicName) // prints: number

This area of the code hasn't changed since mid-December, but I can't remember if that was part of 2.1 or 2.2.

@sandersn Thank you! I can definitely use that. However, I'd love to get type annotations for @type as well.

test.ts

/** @TSType int */
let x: number = 12

/** @type int */
let y: number = 12

The code you posted above works but when I try to get the docs for y, it doesn't work.

var ts = require('typescript')
var program = ts.createProgram(['test.ts'], {})
var checker = program.getTypeChecker()
var test_ts = program.getSourceFiles()[1]
var declName = test_ts.statements[1].declarationList.declarations[0].name
var symbol = checker.getSymbolAtLocation(declName)
var type = checker.getTypeAtLocation(declName)
var tags = symbol.getJsDocTags()
console.log(tags) // prints: []
console.log(type.intrinsicName) // prints: number

What's so special about @type that getJsDocTags does not return it?

/** @type int */
let y: number = 12

are you missing @ symbol ?

@BANG88 Ups, forgot to copy it. Results are the same.

The current design is customised closely to what the language service needs. I didn't think about retrieving jsdoc when using typescript as a parser. So @type is ignored in typescript because type annotations always win, and in JavaScript @type is just reported as the declaration's type.

Probably getJsDocTags could add a parameter to say whether to retrieve all tags or only custom tags. But either the parser would have to store all tags, or I would need to write code to stuff known tags back into the tag list, since they're parsed into their own, named properties.

Any update? I don't need @type, but @param and @returns are needed for description and summary in json schema. What are

their own, named properties

May be I can use them?

There are internal functions for this but they are not exposed in the d.ts file:

  • getJSDocParameterTags -- gets @param tags
  • getJSDocType -- gets the TypeNode for a node, regardless of whether it came from @type or a containing function's @param tag.
  • getJSDocAugmentsTag -- @augments
  • getJSDocClassTag -- @class
  • getJSDocReturnType --@returns
  • getJSDocTemplateType -- @template

After talking to @weswigham and @rbuckton, we don't see any reason to keep the functions internal. I'll send a PR to make them public.