typedoc 0.24.0-beta.3 → 0.24.0-beta.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/dist/lib/cli.js +5 -2
- package/dist/lib/converter/comments/blockLexer.d.ts +2 -1
- package/dist/lib/converter/comments/blockLexer.js +45 -4
- package/dist/lib/converter/comments/discovery.d.ts +7 -2
- package/dist/lib/converter/comments/discovery.js +61 -20
- package/dist/lib/converter/comments/index.d.ts +3 -3
- package/dist/lib/converter/comments/index.js +18 -17
- package/dist/lib/converter/comments/lexer.d.ts +2 -0
- package/dist/lib/converter/comments/linkResolver.d.ts +2 -2
- package/dist/lib/converter/comments/linkResolver.js +25 -20
- package/dist/lib/converter/comments/parser.js +6 -2
- package/dist/lib/converter/context.d.ts +3 -11
- package/dist/lib/converter/context.js +13 -19
- package/dist/lib/converter/converter.d.ts +2 -0
- package/dist/lib/converter/converter.js +6 -3
- package/dist/lib/converter/factories/signature.js +16 -7
- package/dist/lib/converter/jsdoc.js +3 -3
- package/dist/lib/converter/plugins/CommentPlugin.js +18 -0
- package/dist/lib/converter/plugins/InheritDocPlugin.js +2 -1
- package/dist/lib/converter/plugins/SourcePlugin.js +3 -0
- package/dist/lib/converter/symbols.js +48 -6
- package/dist/lib/converter/types.js +2 -2
- package/dist/lib/models/comments/comment.d.ts +6 -6
- package/dist/lib/models/comments/comment.js +26 -10
- package/dist/lib/models/reflections/abstract.js +1 -1
- package/dist/lib/models/reflections/project.js +1 -1
- package/dist/lib/output/events.js +4 -4
- package/dist/lib/output/renderer.d.ts +3 -0
- package/dist/lib/output/renderer.js +6 -2
- package/dist/lib/output/themes/default/DefaultTheme.js +7 -1
- package/dist/lib/output/themes/default/DefaultThemeRenderContext.d.ts +1 -1
- package/dist/lib/output/themes/default/DefaultThemeRenderContext.js +9 -3
- package/dist/lib/output/themes/default/layouts/default.js +5 -5
- package/dist/lib/output/themes/default/partials/typeParameters.js +1 -0
- package/dist/lib/output/themes/default/templates/reflection.js +2 -1
- package/dist/lib/output/themes/lib.js +1 -0
- package/dist/lib/serialization/schema.d.ts +8 -7
- package/dist/lib/serialization/serializer.js +1 -1
- package/dist/lib/utils/component.js +1 -1
- package/dist/lib/utils/entry-point.js +2 -2
- package/dist/lib/utils/options/declaration.d.ts +3 -0
- package/dist/lib/utils/options/sources/typedoc.js +24 -2
- package/dist/lib/utils/options/tsdoc-defaults.d.ts +2 -2
- package/dist/lib/utils/options/tsdoc-defaults.js +4 -0
- package/dist/lib/utils/package-manifest.js +4 -4
- package/package.json +8 -8
- package/static/style.css +4 -5
- package/tsdoc.json +24 -0
package/README.md
CHANGED
|
@@ -41,7 +41,7 @@ By default, TypeDoc will search for a file called `index` under the directory.
|
|
|
41
41
|
If your codebase is comprised of one or more npm packages, you can build documentation for each of them individually
|
|
42
42
|
and merge the results together into a single site by setting `entryPointStrategy` to `packages`. In this mode TypeDoc
|
|
43
43
|
requires configuration to be present in each directory to specify the entry points. For an example setup, see
|
|
44
|
-
|
|
44
|
+
https://github.com/Gerrit0/typedoc-packages-example
|
|
45
45
|
|
|
46
46
|
### Arguments
|
|
47
47
|
|
package/dist/lib/cli.js
CHANGED
|
@@ -93,12 +93,15 @@ async function run(app) {
|
|
|
93
93
|
app.logger.hasWarnings()) {
|
|
94
94
|
return ExitCodes.CompileError;
|
|
95
95
|
}
|
|
96
|
+
const preValidationWarnCount = app.logger.warningCount;
|
|
96
97
|
app.validate(project);
|
|
98
|
+
const hadValidationWarnings = app.logger.warningCount !== preValidationWarnCount;
|
|
97
99
|
if (app.logger.hasErrors()) {
|
|
98
100
|
return ExitCodes.ValidationError;
|
|
99
101
|
}
|
|
100
|
-
if (
|
|
101
|
-
app.
|
|
102
|
+
if (hadValidationWarnings &&
|
|
103
|
+
(app.options.getValue("treatWarningsAsErrors") ||
|
|
104
|
+
app.options.getValue("treatValidationWarningsAsErrors"))) {
|
|
102
105
|
return ExitCodes.ValidationError;
|
|
103
106
|
}
|
|
104
107
|
if (app.options.getValue("emit") !== "none") {
|
|
@@ -1,2 +1,3 @@
|
|
|
1
|
+
import ts from "typescript";
|
|
1
2
|
import { Token } from "./lexer";
|
|
2
|
-
export declare function lexBlockComment(file: string, pos?: number, end?: number): Generator<Token, undefined, undefined>;
|
|
3
|
+
export declare function lexBlockComment(file: string, pos?: number, end?: number, jsDoc?: ts.JSDoc | undefined, checker?: ts.TypeChecker | undefined): Generator<Token, undefined, undefined>;
|
|
@@ -1,11 +1,17 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
2
5
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
6
|
exports.lexBlockComment = void 0;
|
|
7
|
+
const typescript_1 = __importDefault(require("typescript"));
|
|
4
8
|
const lexer_1 = require("./lexer");
|
|
5
|
-
|
|
9
|
+
const ReflectionSymbolId_1 = require("../../models/reflections/ReflectionSymbolId");
|
|
10
|
+
const symbols_1 = require("../utils/symbols");
|
|
11
|
+
function* lexBlockComment(file, pos = 0, end = file.length, jsDoc = undefined, checker = undefined) {
|
|
6
12
|
// Wrapper around our real lex function to collapse adjacent text tokens.
|
|
7
13
|
let textToken;
|
|
8
|
-
for (const token of lexBlockComment2(file, pos, end)) {
|
|
14
|
+
for (const token of lexBlockComment2(file, pos, end, getLinkTags(jsDoc), checker)) {
|
|
9
15
|
if (token.kind === lexer_1.TokenSyntaxKind.Text) {
|
|
10
16
|
if (textToken) {
|
|
11
17
|
textToken.text += token.text;
|
|
@@ -28,7 +34,21 @@ function* lexBlockComment(file, pos = 0, end = file.length) {
|
|
|
28
34
|
return;
|
|
29
35
|
}
|
|
30
36
|
exports.lexBlockComment = lexBlockComment;
|
|
31
|
-
function
|
|
37
|
+
function getLinkTags(jsDoc) {
|
|
38
|
+
const result = [];
|
|
39
|
+
if (!jsDoc || typeof jsDoc.comment !== "object")
|
|
40
|
+
return result;
|
|
41
|
+
for (const part of jsDoc.comment) {
|
|
42
|
+
switch (part.kind) {
|
|
43
|
+
case typescript_1.default.SyntaxKind.JSDocLink:
|
|
44
|
+
case typescript_1.default.SyntaxKind.JSDocLinkCode:
|
|
45
|
+
case typescript_1.default.SyntaxKind.JSDocLinkPlain:
|
|
46
|
+
result.push(part);
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
return result;
|
|
50
|
+
}
|
|
51
|
+
function* lexBlockComment2(file, pos, end, linkTags, checker) {
|
|
32
52
|
pos += 2; // Leading '/*'
|
|
33
53
|
end -= 2; // Trailing '*/'
|
|
34
54
|
if (pos < end && file[pos] === "*") {
|
|
@@ -47,6 +67,7 @@ function* lexBlockComment2(file, pos, end) {
|
|
|
47
67
|
}
|
|
48
68
|
let lineStart = true;
|
|
49
69
|
let braceStartsType = false;
|
|
70
|
+
let linkTagIndex = 0;
|
|
50
71
|
for (;;) {
|
|
51
72
|
if (pos >= end) {
|
|
52
73
|
return;
|
|
@@ -171,7 +192,9 @@ function* lexBlockComment2(file, pos, end) {
|
|
|
171
192
|
if (lookahead !== pos + 1 &&
|
|
172
193
|
(lookahead === end || /\s/.test(file[lookahead]))) {
|
|
173
194
|
braceStartsType = true;
|
|
174
|
-
|
|
195
|
+
const token = makeToken(lexer_1.TokenSyntaxKind.Tag, lookahead - pos);
|
|
196
|
+
attachLinkTagResult(token);
|
|
197
|
+
yield token;
|
|
175
198
|
break;
|
|
176
199
|
}
|
|
177
200
|
}
|
|
@@ -213,6 +236,24 @@ function* lexBlockComment2(file, pos, end) {
|
|
|
213
236
|
}
|
|
214
237
|
}
|
|
215
238
|
}
|
|
239
|
+
function attachLinkTagResult(token) {
|
|
240
|
+
// We might need to skip link tags if someone has link tags inside of an example comment
|
|
241
|
+
// pos-1 for opening brace, TS doesn't allow spaces between opening brace and @ sign as of 5.0.2
|
|
242
|
+
while (linkTagIndex < linkTags.length &&
|
|
243
|
+
linkTags[linkTagIndex].pos < token.pos - 1) {
|
|
244
|
+
linkTagIndex++;
|
|
245
|
+
}
|
|
246
|
+
if (linkTagIndex < linkTags.length &&
|
|
247
|
+
linkTags[linkTagIndex].pos === token.pos - 1) {
|
|
248
|
+
const link = linkTags[linkTagIndex];
|
|
249
|
+
if (link.name) {
|
|
250
|
+
const tsTarget = checker?.getSymbolAtLocation(link.name);
|
|
251
|
+
if (tsTarget) {
|
|
252
|
+
token.linkTarget = new ReflectionSymbolId_1.ReflectionSymbolId((0, symbols_1.resolveAliasedSymbol)(tsTarget, checker));
|
|
253
|
+
}
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
}
|
|
216
257
|
function makeToken(kind, size) {
|
|
217
258
|
const start = pos;
|
|
218
259
|
pos += size;
|
|
@@ -2,5 +2,10 @@ import ts from "typescript";
|
|
|
2
2
|
import { ReflectionKind } from "../../models";
|
|
3
3
|
import { Logger } from "../../utils";
|
|
4
4
|
import { CommentStyle } from "../../utils/options/declaration";
|
|
5
|
-
export
|
|
6
|
-
|
|
5
|
+
export interface DiscoveredComment {
|
|
6
|
+
file: ts.SourceFile;
|
|
7
|
+
ranges: ts.CommentRange[];
|
|
8
|
+
jsDoc: ts.JSDoc | undefined;
|
|
9
|
+
}
|
|
10
|
+
export declare function discoverComment(symbol: ts.Symbol, kind: ReflectionKind, logger: Logger, commentStyle: CommentStyle): DiscoveredComment | undefined;
|
|
11
|
+
export declare function discoverSignatureComment(declaration: ts.SignatureDeclaration | ts.JSDocSignature, commentStyle: CommentStyle): DiscoveredComment | undefined;
|
|
@@ -9,6 +9,20 @@ const models_1 = require("../../models");
|
|
|
9
9
|
const utils_1 = require("../../utils");
|
|
10
10
|
const declaration_1 = require("../../utils/options/declaration");
|
|
11
11
|
const paths_1 = require("../../utils/paths");
|
|
12
|
+
const assert_1 = require("assert");
|
|
13
|
+
const variablePropertyKinds = [
|
|
14
|
+
typescript_1.default.SyntaxKind.PropertyDeclaration,
|
|
15
|
+
typescript_1.default.SyntaxKind.PropertySignature,
|
|
16
|
+
typescript_1.default.SyntaxKind.BinaryExpression,
|
|
17
|
+
typescript_1.default.SyntaxKind.PropertyAssignment,
|
|
18
|
+
// class X { constructor(/** Comment */ readonly z: string) }
|
|
19
|
+
typescript_1.default.SyntaxKind.Parameter,
|
|
20
|
+
// Variable values
|
|
21
|
+
typescript_1.default.SyntaxKind.VariableDeclaration,
|
|
22
|
+
typescript_1.default.SyntaxKind.BindingElement,
|
|
23
|
+
typescript_1.default.SyntaxKind.ExportAssignment,
|
|
24
|
+
typescript_1.default.SyntaxKind.PropertyAccessExpression,
|
|
25
|
+
];
|
|
12
26
|
// Note: This does NOT include JSDoc syntax kinds. This is important!
|
|
13
27
|
// Comments from @typedef and @callback tags are handled specially by
|
|
14
28
|
// the JSDoc converter because we only want part of the comment when
|
|
@@ -22,6 +36,11 @@ const wantedKinds = {
|
|
|
22
36
|
typescript_1.default.SyntaxKind.BindingElement,
|
|
23
37
|
typescript_1.default.SyntaxKind.ExportSpecifier,
|
|
24
38
|
typescript_1.default.SyntaxKind.NamespaceExport,
|
|
39
|
+
// @namespace support
|
|
40
|
+
typescript_1.default.SyntaxKind.VariableDeclaration,
|
|
41
|
+
typescript_1.default.SyntaxKind.BindingElement,
|
|
42
|
+
typescript_1.default.SyntaxKind.ExportAssignment,
|
|
43
|
+
typescript_1.default.SyntaxKind.PropertyAccessExpression,
|
|
25
44
|
],
|
|
26
45
|
[models_1.ReflectionKind.Enum]: [
|
|
27
46
|
typescript_1.default.SyntaxKind.EnumDeclaration,
|
|
@@ -33,12 +52,7 @@ const wantedKinds = {
|
|
|
33
52
|
typescript_1.default.SyntaxKind.PropertyAssignment,
|
|
34
53
|
typescript_1.default.SyntaxKind.PropertySignature,
|
|
35
54
|
],
|
|
36
|
-
[models_1.ReflectionKind.Variable]:
|
|
37
|
-
typescript_1.default.SyntaxKind.VariableDeclaration,
|
|
38
|
-
typescript_1.default.SyntaxKind.BindingElement,
|
|
39
|
-
typescript_1.default.SyntaxKind.ExportAssignment,
|
|
40
|
-
typescript_1.default.SyntaxKind.PropertyAccessExpression,
|
|
41
|
-
],
|
|
55
|
+
[models_1.ReflectionKind.Variable]: variablePropertyKinds,
|
|
42
56
|
[models_1.ReflectionKind.Function]: [
|
|
43
57
|
typescript_1.default.SyntaxKind.FunctionDeclaration,
|
|
44
58
|
typescript_1.default.SyntaxKind.BindingElement,
|
|
@@ -50,16 +64,12 @@ const wantedKinds = {
|
|
|
50
64
|
typescript_1.default.SyntaxKind.ClassDeclaration,
|
|
51
65
|
typescript_1.default.SyntaxKind.BindingElement,
|
|
52
66
|
],
|
|
53
|
-
[models_1.ReflectionKind.Interface]: [
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
typescript_1.default.SyntaxKind.PropertyDeclaration,
|
|
57
|
-
typescript_1.default.SyntaxKind.PropertySignature,
|
|
58
|
-
typescript_1.default.SyntaxKind.BinaryExpression,
|
|
59
|
-
typescript_1.default.SyntaxKind.PropertyAssignment,
|
|
60
|
-
// class X { constructor(/** Comment */ readonly z: string) }
|
|
61
|
-
typescript_1.default.SyntaxKind.Parameter,
|
|
67
|
+
[models_1.ReflectionKind.Interface]: [
|
|
68
|
+
typescript_1.default.SyntaxKind.InterfaceDeclaration,
|
|
69
|
+
typescript_1.default.SyntaxKind.TypeAliasDeclaration,
|
|
62
70
|
],
|
|
71
|
+
[models_1.ReflectionKind.Constructor]: [typescript_1.default.SyntaxKind.Constructor],
|
|
72
|
+
[models_1.ReflectionKind.Property]: variablePropertyKinds,
|
|
63
73
|
[models_1.ReflectionKind.Method]: [
|
|
64
74
|
typescript_1.default.SyntaxKind.FunctionDeclaration,
|
|
65
75
|
typescript_1.default.SyntaxKind.MethodDeclaration,
|
|
@@ -120,7 +130,11 @@ function discoverComment(symbol, kind, logger, commentStyle) {
|
|
|
120
130
|
}
|
|
121
131
|
const selectedDocComment = comments.find((ranges) => permittedRange(text, ranges, commentStyle));
|
|
122
132
|
if (selectedDocComment) {
|
|
123
|
-
discovered.push(
|
|
133
|
+
discovered.push({
|
|
134
|
+
file: decl.getSourceFile(),
|
|
135
|
+
ranges: selectedDocComment,
|
|
136
|
+
jsDoc: findJsDocForComment(node, selectedDocComment),
|
|
137
|
+
});
|
|
124
138
|
}
|
|
125
139
|
}
|
|
126
140
|
}
|
|
@@ -131,9 +145,9 @@ function discoverComment(symbol, kind, logger, commentStyle) {
|
|
|
131
145
|
return discovered[0];
|
|
132
146
|
default: {
|
|
133
147
|
logger.warn(`${symbol.name} has multiple declarations with a comment. An arbitrary comment will be used.`);
|
|
134
|
-
const locations = discovered.map((
|
|
135
|
-
const path = (0, paths_1.nicePath)(
|
|
136
|
-
const line = typescript_1.default.getLineAndCharacterOfPosition(
|
|
148
|
+
const locations = discovered.map(({ file, ranges: [{ pos }] }) => {
|
|
149
|
+
const path = (0, paths_1.nicePath)(file.fileName);
|
|
150
|
+
const line = typescript_1.default.getLineAndCharacterOfPosition(file, pos).line + 1;
|
|
137
151
|
return `${path}:${line}`;
|
|
138
152
|
});
|
|
139
153
|
logger.info(`The comments for ${symbol.name} are declared at:\n\t${locations.join("\n\t")}`);
|
|
@@ -147,15 +161,42 @@ function discoverSignatureComment(declaration, commentStyle) {
|
|
|
147
161
|
if (!node) {
|
|
148
162
|
return;
|
|
149
163
|
}
|
|
164
|
+
if (typescript_1.default.isJSDocSignature(node)) {
|
|
165
|
+
const comment = node.parent.parent;
|
|
166
|
+
(0, assert_1.ok)(typescript_1.default.isJSDoc(comment));
|
|
167
|
+
return {
|
|
168
|
+
file: node.getSourceFile(),
|
|
169
|
+
ranges: [
|
|
170
|
+
{
|
|
171
|
+
kind: typescript_1.default.SyntaxKind.MultiLineCommentTrivia,
|
|
172
|
+
pos: comment.pos,
|
|
173
|
+
end: comment.end,
|
|
174
|
+
},
|
|
175
|
+
],
|
|
176
|
+
jsDoc: undefined,
|
|
177
|
+
};
|
|
178
|
+
}
|
|
150
179
|
const text = node.getSourceFile().text;
|
|
151
180
|
const comments = collectCommentRanges(typescript_1.default.getLeadingCommentRanges(text, node.pos));
|
|
152
181
|
comments.reverse();
|
|
153
182
|
const comment = comments.find((ranges) => permittedRange(text, ranges, commentStyle));
|
|
154
183
|
if (comment) {
|
|
155
|
-
return
|
|
184
|
+
return {
|
|
185
|
+
file: node.getSourceFile(),
|
|
186
|
+
ranges: comment,
|
|
187
|
+
jsDoc: findJsDocForComment(node, comment),
|
|
188
|
+
};
|
|
156
189
|
}
|
|
157
190
|
}
|
|
158
191
|
exports.discoverSignatureComment = discoverSignatureComment;
|
|
192
|
+
function findJsDocForComment(node, ranges) {
|
|
193
|
+
if (ranges[0].kind === typescript_1.default.SyntaxKind.MultiLineCommentTrivia) {
|
|
194
|
+
const jsDocs = typescript_1.default
|
|
195
|
+
.getJSDocCommentsAndTags(node)
|
|
196
|
+
.map((doc) => typescript_1.default.findAncestor(doc, typescript_1.default.isJSDoc));
|
|
197
|
+
return jsDocs.find((doc) => doc.pos === ranges[0].pos);
|
|
198
|
+
}
|
|
199
|
+
}
|
|
159
200
|
/**
|
|
160
201
|
* Check whether the given module declaration is the topmost.
|
|
161
202
|
*
|
|
@@ -7,6 +7,6 @@ export interface CommentParserConfig {
|
|
|
7
7
|
inlineTags: Set<string>;
|
|
8
8
|
modifierTags: Set<string>;
|
|
9
9
|
}
|
|
10
|
-
export declare function getComment(symbol: ts.Symbol, kind: ReflectionKind, config: CommentParserConfig, logger: Logger, commentStyle: CommentStyle): Comment | undefined;
|
|
11
|
-
export declare function getSignatureComment(declaration: ts.SignatureDeclaration | ts.JSDocSignature, config: CommentParserConfig, logger: Logger, commentStyle: CommentStyle): Comment | undefined;
|
|
12
|
-
export declare function getJsDocComment(declaration: ts.JSDocPropertyLikeTag | ts.JSDocCallbackTag | ts.JSDocTypedefTag | ts.JSDocTemplateTag | ts.JSDocEnumTag, config: CommentParserConfig, logger: Logger): Comment | undefined;
|
|
10
|
+
export declare function getComment(symbol: ts.Symbol, kind: ReflectionKind, config: CommentParserConfig, logger: Logger, commentStyle: CommentStyle, checker: ts.TypeChecker): Comment | undefined;
|
|
11
|
+
export declare function getSignatureComment(declaration: ts.SignatureDeclaration | ts.JSDocSignature, config: CommentParserConfig, logger: Logger, commentStyle: CommentStyle, checker: ts.TypeChecker): Comment | undefined;
|
|
12
|
+
export declare function getJsDocComment(declaration: ts.JSDocPropertyLikeTag | ts.JSDocCallbackTag | ts.JSDocTypedefTag | ts.JSDocTemplateTag | ts.JSDocEnumTag, config: CommentParserConfig, logger: Logger, checker: ts.TypeChecker): Comment | undefined;
|
|
@@ -19,10 +19,10 @@ const jsDocCommentKinds = [
|
|
|
19
19
|
typescript_1.default.SyntaxKind.JSDocEnumTag,
|
|
20
20
|
];
|
|
21
21
|
const commentCache = new WeakMap();
|
|
22
|
-
function getCommentWithCache(discovered, config, logger) {
|
|
22
|
+
function getCommentWithCache(discovered, config, logger, checker) {
|
|
23
23
|
if (!discovered)
|
|
24
24
|
return;
|
|
25
|
-
const
|
|
25
|
+
const { file, ranges, jsDoc } = discovered;
|
|
26
26
|
const cache = commentCache.get(file) || new Map();
|
|
27
27
|
if (cache?.has(ranges[0].pos)) {
|
|
28
28
|
return cache.get(ranges[0].pos).clone();
|
|
@@ -30,7 +30,7 @@ function getCommentWithCache(discovered, config, logger) {
|
|
|
30
30
|
let comment;
|
|
31
31
|
switch (ranges[0].kind) {
|
|
32
32
|
case typescript_1.default.SyntaxKind.MultiLineCommentTrivia:
|
|
33
|
-
comment = (0, parser_1.parseComment)((0, blockLexer_1.lexBlockComment)(file.text, ranges[0].pos, ranges[0].end), config, file, logger);
|
|
33
|
+
comment = (0, parser_1.parseComment)((0, blockLexer_1.lexBlockComment)(file.text, ranges[0].pos, ranges[0].end, jsDoc, checker), config, file, logger);
|
|
34
34
|
break;
|
|
35
35
|
case typescript_1.default.SyntaxKind.SingleLineCommentTrivia:
|
|
36
36
|
comment = (0, parser_1.parseComment)((0, lineLexer_1.lexLineComments)(file.text, ranges), config, file, logger);
|
|
@@ -42,8 +42,8 @@ function getCommentWithCache(discovered, config, logger) {
|
|
|
42
42
|
commentCache.set(file, cache);
|
|
43
43
|
return comment.clone();
|
|
44
44
|
}
|
|
45
|
-
function getCommentImpl(commentSource, config, logger, moduleComment) {
|
|
46
|
-
const comment = getCommentWithCache(commentSource, config, logger);
|
|
45
|
+
function getCommentImpl(commentSource, config, logger, moduleComment, checker) {
|
|
46
|
+
const comment = getCommentWithCache(commentSource, config, logger, checker);
|
|
47
47
|
if (moduleComment && comment) {
|
|
48
48
|
// Module comment, make sure it is tagged with @packageDocumentation or @module.
|
|
49
49
|
// If it isn't then the comment applies to the first statement in the file, so throw it away.
|
|
@@ -61,35 +61,35 @@ function getCommentImpl(commentSource, config, logger, moduleComment) {
|
|
|
61
61
|
}
|
|
62
62
|
return comment;
|
|
63
63
|
}
|
|
64
|
-
function getComment(symbol, kind, config, logger, commentStyle) {
|
|
64
|
+
function getComment(symbol, kind, config, logger, commentStyle, checker) {
|
|
65
65
|
const declarations = symbol.declarations || [];
|
|
66
66
|
if (declarations.length &&
|
|
67
67
|
declarations.every((d) => jsDocCommentKinds.includes(d.kind))) {
|
|
68
|
-
return getJsDocComment(declarations[0], config, logger);
|
|
68
|
+
return getJsDocComment(declarations[0], config, logger, checker);
|
|
69
69
|
}
|
|
70
|
-
const comment = getCommentImpl((0, discovery_1.discoverComment)(symbol, kind, logger, commentStyle), config, logger, declarations.some(typescript_1.default.isSourceFile));
|
|
70
|
+
const comment = getCommentImpl((0, discovery_1.discoverComment)(symbol, kind, logger, commentStyle), config, logger, declarations.some(typescript_1.default.isSourceFile), checker);
|
|
71
71
|
if (!comment && kind === models_1.ReflectionKind.Property) {
|
|
72
|
-
return getConstructorParamPropertyComment(symbol, config, logger, commentStyle);
|
|
72
|
+
return getConstructorParamPropertyComment(symbol, config, logger, commentStyle, checker);
|
|
73
73
|
}
|
|
74
74
|
return comment;
|
|
75
75
|
}
|
|
76
76
|
exports.getComment = getComment;
|
|
77
|
-
function getConstructorParamPropertyComment(symbol, config, logger, commentStyle) {
|
|
77
|
+
function getConstructorParamPropertyComment(symbol, config, logger, commentStyle, checker) {
|
|
78
78
|
const decl = symbol.declarations?.find(typescript_1.default.isParameter);
|
|
79
79
|
if (!decl)
|
|
80
80
|
return;
|
|
81
81
|
const ctor = decl.parent;
|
|
82
|
-
const comment = getSignatureComment(ctor, config, logger, commentStyle);
|
|
82
|
+
const comment = getSignatureComment(ctor, config, logger, commentStyle, checker);
|
|
83
83
|
const paramTag = comment?.getIdentifiedTag(symbol.name, "@param");
|
|
84
84
|
if (paramTag) {
|
|
85
85
|
return new models_1.Comment(paramTag.content);
|
|
86
86
|
}
|
|
87
87
|
}
|
|
88
|
-
function getSignatureComment(declaration, config, logger, commentStyle) {
|
|
89
|
-
return getCommentImpl((0, discovery_1.discoverSignatureComment)(declaration, commentStyle), config, logger, false);
|
|
88
|
+
function getSignatureComment(declaration, config, logger, commentStyle, checker) {
|
|
89
|
+
return getCommentImpl((0, discovery_1.discoverSignatureComment)(declaration, commentStyle), config, logger, false, checker);
|
|
90
90
|
}
|
|
91
91
|
exports.getSignatureComment = getSignatureComment;
|
|
92
|
-
function getJsDocComment(declaration, config, logger) {
|
|
92
|
+
function getJsDocComment(declaration, config, logger, checker) {
|
|
93
93
|
const file = declaration.getSourceFile();
|
|
94
94
|
// First, get the whole comment. We know we'll need all of it.
|
|
95
95
|
let parent = declaration.parent;
|
|
@@ -97,16 +97,17 @@ function getJsDocComment(declaration, config, logger) {
|
|
|
97
97
|
parent = parent.parent;
|
|
98
98
|
}
|
|
99
99
|
// Then parse it.
|
|
100
|
-
const comment = getCommentWithCache(
|
|
100
|
+
const comment = getCommentWithCache({
|
|
101
101
|
file,
|
|
102
|
-
[
|
|
102
|
+
ranges: [
|
|
103
103
|
{
|
|
104
104
|
kind: typescript_1.default.SyntaxKind.MultiLineCommentTrivia,
|
|
105
105
|
pos: parent.pos,
|
|
106
106
|
end: parent.end,
|
|
107
107
|
},
|
|
108
108
|
],
|
|
109
|
-
|
|
109
|
+
jsDoc: parent,
|
|
110
|
+
}, config, logger, checker);
|
|
110
111
|
// And pull out the tag we actually care about.
|
|
111
112
|
if (typescript_1.default.isJSDocEnumTag(declaration)) {
|
|
112
113
|
return new models_1.Comment(comment.getTag("@enum")?.content);
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import type { ReflectionSymbolId } from "../../models";
|
|
1
2
|
export declare enum TokenSyntaxKind {
|
|
2
3
|
Text = "text",
|
|
3
4
|
NewLine = "new_line",
|
|
@@ -11,4 +12,5 @@ export interface Token {
|
|
|
11
12
|
kind: TokenSyntaxKind;
|
|
12
13
|
text: string;
|
|
13
14
|
pos: number;
|
|
15
|
+
linkTarget?: ReflectionSymbolId;
|
|
14
16
|
}
|
|
@@ -5,5 +5,5 @@ export type ExternalResolveResult = {
|
|
|
5
5
|
caption?: string;
|
|
6
6
|
};
|
|
7
7
|
export type ExternalSymbolResolver = (ref: DeclarationReference, refl: Reflection, part: Readonly<CommentDisplayPart> | undefined) => ExternalResolveResult | string | undefined;
|
|
8
|
-
export declare function resolveLinks(comment: Comment, reflection: Reflection, externalResolver: ExternalSymbolResolver): void;
|
|
9
|
-
export declare function resolvePartLinks(reflection: Reflection, parts: readonly CommentDisplayPart[], externalResolver: ExternalSymbolResolver): CommentDisplayPart[];
|
|
8
|
+
export declare function resolveLinks(comment: Comment, reflection: Reflection, externalResolver: ExternalSymbolResolver, useTsResolution: boolean): void;
|
|
9
|
+
export declare function resolvePartLinks(reflection: Reflection, parts: readonly CommentDisplayPart[], externalResolver: ExternalSymbolResolver, useTsResolution: boolean): CommentDisplayPart[];
|
|
@@ -9,40 +9,48 @@ const models_1 = require("../../models");
|
|
|
9
9
|
const declarationReference_1 = require("./declarationReference");
|
|
10
10
|
const declarationReferenceResolver_1 = require("./declarationReferenceResolver");
|
|
11
11
|
const urlPrefix = /^(http|ftp)s?:\/\//;
|
|
12
|
-
function resolveLinks(comment, reflection, externalResolver) {
|
|
13
|
-
comment.summary = resolvePartLinks(reflection, comment.summary, externalResolver);
|
|
12
|
+
function resolveLinks(comment, reflection, externalResolver, useTsResolution) {
|
|
13
|
+
comment.summary = resolvePartLinks(reflection, comment.summary, externalResolver, useTsResolution);
|
|
14
14
|
for (const tag of comment.blockTags) {
|
|
15
|
-
tag.content = resolvePartLinks(reflection, tag.content, externalResolver);
|
|
15
|
+
tag.content = resolvePartLinks(reflection, tag.content, externalResolver, useTsResolution);
|
|
16
16
|
}
|
|
17
17
|
if (reflection instanceof models_1.DeclarationReflection && reflection.readme) {
|
|
18
|
-
reflection.readme = resolvePartLinks(reflection, reflection.readme, externalResolver);
|
|
18
|
+
reflection.readme = resolvePartLinks(reflection, reflection.readme, externalResolver, useTsResolution);
|
|
19
19
|
}
|
|
20
20
|
}
|
|
21
21
|
exports.resolveLinks = resolveLinks;
|
|
22
|
-
function resolvePartLinks(reflection, parts, externalResolver) {
|
|
23
|
-
return parts.flatMap((part) => processPart(reflection, part, externalResolver));
|
|
22
|
+
function resolvePartLinks(reflection, parts, externalResolver, useTsResolution) {
|
|
23
|
+
return parts.flatMap((part) => processPart(reflection, part, externalResolver, useTsResolution));
|
|
24
24
|
}
|
|
25
25
|
exports.resolvePartLinks = resolvePartLinks;
|
|
26
|
-
function processPart(reflection, part, externalResolver) {
|
|
26
|
+
function processPart(reflection, part, externalResolver, useTsResolution) {
|
|
27
27
|
if (part.kind === "inline-tag") {
|
|
28
28
|
if (part.tag === "@link" ||
|
|
29
29
|
part.tag === "@linkcode" ||
|
|
30
30
|
part.tag === "@linkplain") {
|
|
31
|
-
return resolveLinkTag(reflection, part, externalResolver);
|
|
31
|
+
return resolveLinkTag(reflection, part, externalResolver, useTsResolution);
|
|
32
32
|
}
|
|
33
33
|
}
|
|
34
34
|
return part;
|
|
35
35
|
}
|
|
36
|
-
function resolveLinkTag(reflection, part, externalResolver) {
|
|
36
|
+
function resolveLinkTag(reflection, part, externalResolver, useTsResolution) {
|
|
37
|
+
let defaultDisplayText = "";
|
|
37
38
|
let pos = 0;
|
|
38
39
|
const end = part.text.length;
|
|
39
40
|
while (pos < end && typescript_1.default.isWhiteSpaceLike(part.text.charCodeAt(pos))) {
|
|
40
41
|
pos++;
|
|
41
42
|
}
|
|
42
|
-
// Try to parse one
|
|
43
|
-
const declRef = (0, declarationReference_1.parseDeclarationReference)(part.text, pos, end);
|
|
44
43
|
let target;
|
|
45
|
-
|
|
44
|
+
if (useTsResolution && part.target instanceof models_1.ReflectionSymbolId) {
|
|
45
|
+
target = reflection.project.getReflectionFromSymbolId(part.target);
|
|
46
|
+
if (target) {
|
|
47
|
+
pos = end;
|
|
48
|
+
defaultDisplayText =
|
|
49
|
+
part.text.replace(/^\s*[A-Z_$][\w$]*[ |]*/i, "") || target.name;
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
// Try to parse a declaration reference if we didn't use the TS symbol for resolution
|
|
53
|
+
const declRef = !target && (0, declarationReference_1.parseDeclarationReference)(part.text, pos, end);
|
|
46
54
|
if (declRef) {
|
|
47
55
|
// Got one, great! Try to resolve the link
|
|
48
56
|
target = (0, declarationReferenceResolver_1.resolveDeclarationReference)(reflection, declRef[0]);
|
|
@@ -65,14 +73,11 @@ function resolveLinkTag(reflection, part, externalResolver) {
|
|
|
65
73
|
}
|
|
66
74
|
}
|
|
67
75
|
}
|
|
68
|
-
if (!target) {
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
pos = target.length;
|
|
74
|
-
defaultDisplayText = target;
|
|
75
|
-
}
|
|
76
|
+
if (!target && urlPrefix.test(part.text)) {
|
|
77
|
+
const wsIndex = part.text.search(/\s/);
|
|
78
|
+
target = wsIndex === -1 ? part.text : part.text.substring(0, wsIndex);
|
|
79
|
+
pos = target.length;
|
|
80
|
+
defaultDisplayText = target;
|
|
76
81
|
}
|
|
77
82
|
// Remaining text after an optional pipe is the link text, so advance
|
|
78
83
|
// until that's consumed.
|
|
@@ -299,9 +299,13 @@ function inlineTag(lexer, block, config, warning) {
|
|
|
299
299
|
else {
|
|
300
300
|
lexer.take(); // Close brace
|
|
301
301
|
}
|
|
302
|
-
|
|
302
|
+
const inlineTag = {
|
|
303
303
|
kind: "inline-tag",
|
|
304
304
|
tag: tagName.text,
|
|
305
305
|
text: content.join(""),
|
|
306
|
-
}
|
|
306
|
+
};
|
|
307
|
+
if (tagName.linkTarget) {
|
|
308
|
+
inlineTag.target = tagName.linkTarget;
|
|
309
|
+
}
|
|
310
|
+
block.push(inlineTag);
|
|
307
311
|
}
|
|
@@ -31,13 +31,9 @@ export declare class Context {
|
|
|
31
31
|
* The scope or parent reflection that is currently processed.
|
|
32
32
|
*/
|
|
33
33
|
readonly scope: Reflection;
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
/** @internal */
|
|
37
|
-
setConvertingTypeNode(): void;
|
|
38
|
-
/** @internal */
|
|
34
|
+
convertingTypeNode: boolean;
|
|
35
|
+
convertingClassOrInterface: boolean;
|
|
39
36
|
shouldBeStatic: boolean;
|
|
40
|
-
private convertingTypeNode;
|
|
41
37
|
/**
|
|
42
38
|
* Create a new Context instance.
|
|
43
39
|
*
|
|
@@ -46,11 +42,7 @@ export declare class Context {
|
|
|
46
42
|
*/
|
|
47
43
|
constructor(converter: Converter, programs: readonly ts.Program[], project: ProjectReflection, scope?: Context["scope"]);
|
|
48
44
|
/** @internal */
|
|
49
|
-
get logger(): import("../utils
|
|
50
|
-
/**
|
|
51
|
-
* Return the compiler options.
|
|
52
|
-
*/
|
|
53
|
-
getCompilerOptions(): ts.CompilerOptions;
|
|
45
|
+
get logger(): import("../utils").Logger;
|
|
54
46
|
/**
|
|
55
47
|
* Return the type declaration of the given node.
|
|
56
48
|
*
|
|
@@ -30,14 +30,6 @@ class Context {
|
|
|
30
30
|
(0, assert_1.ok)(this._program, "Tried to access Context.program when not converting a source file");
|
|
31
31
|
return this._program;
|
|
32
32
|
}
|
|
33
|
-
/** @internal */
|
|
34
|
-
isConvertingTypeNode() {
|
|
35
|
-
return this.convertingTypeNode;
|
|
36
|
-
}
|
|
37
|
-
/** @internal */
|
|
38
|
-
setConvertingTypeNode() {
|
|
39
|
-
this.convertingTypeNode = true;
|
|
40
|
-
}
|
|
41
33
|
/**
|
|
42
34
|
* Create a new Context instance.
|
|
43
35
|
*
|
|
@@ -45,9 +37,9 @@ class Context {
|
|
|
45
37
|
* @internal
|
|
46
38
|
*/
|
|
47
39
|
constructor(converter, programs, project, scope = project) {
|
|
48
|
-
|
|
49
|
-
this.
|
|
50
|
-
this.
|
|
40
|
+
this.convertingTypeNode = false; // Inherited by withScope
|
|
41
|
+
this.convertingClassOrInterface = false; // Not inherited
|
|
42
|
+
this.shouldBeStatic = false; // Not inherited
|
|
51
43
|
this.converter = converter;
|
|
52
44
|
this.programs = programs;
|
|
53
45
|
this.project = project;
|
|
@@ -57,12 +49,6 @@ class Context {
|
|
|
57
49
|
get logger() {
|
|
58
50
|
return this.converter.application.logger;
|
|
59
51
|
}
|
|
60
|
-
/**
|
|
61
|
-
* Return the compiler options.
|
|
62
|
-
*/
|
|
63
|
-
getCompilerOptions() {
|
|
64
|
-
return this.converter.application.options.getCompilerOptions();
|
|
65
|
-
}
|
|
66
52
|
/**
|
|
67
53
|
* Return the type declaration of the given node.
|
|
68
54
|
*
|
|
@@ -112,6 +98,14 @@ class Context {
|
|
|
112
98
|
// We need this because modules don't always have symbols.
|
|
113
99
|
nameOverride) {
|
|
114
100
|
const name = (0, tsutils_1.getHumanName)(nameOverride ?? exportSymbol?.name ?? symbol?.name ?? "unknown");
|
|
101
|
+
if (this.convertingClassOrInterface) {
|
|
102
|
+
if (kind === index_1.ReflectionKind.Function) {
|
|
103
|
+
kind = index_1.ReflectionKind.Method;
|
|
104
|
+
}
|
|
105
|
+
if (kind === index_1.ReflectionKind.Variable) {
|
|
106
|
+
kind = index_1.ReflectionKind.Property;
|
|
107
|
+
}
|
|
108
|
+
}
|
|
115
109
|
const reflection = new index_1.DeclarationReflection(name, kind, this.scope);
|
|
116
110
|
this.postReflectionCreation(reflection, symbol, exportSymbol);
|
|
117
111
|
return reflection;
|
|
@@ -120,10 +114,10 @@ class Context {
|
|
|
120
114
|
if (exportSymbol &&
|
|
121
115
|
reflection.kind &
|
|
122
116
|
(index_1.ReflectionKind.SomeModule | index_1.ReflectionKind.Reference)) {
|
|
123
|
-
reflection.comment = (0, comments_1.getComment)(exportSymbol, reflection.kind, this.converter.config, this.logger, this.converter.commentStyle);
|
|
117
|
+
reflection.comment = (0, comments_1.getComment)(exportSymbol, reflection.kind, this.converter.config, this.logger, this.converter.commentStyle, this.checker);
|
|
124
118
|
}
|
|
125
119
|
if (symbol && !reflection.comment) {
|
|
126
|
-
reflection.comment = (0, comments_1.getComment)(symbol, reflection.kind, this.converter.config, this.logger, this.converter.commentStyle);
|
|
120
|
+
reflection.comment = (0, comments_1.getComment)(symbol, reflection.kind, this.converter.config, this.logger, this.converter.commentStyle, this.checker);
|
|
127
121
|
}
|
|
128
122
|
if (this.shouldBeStatic) {
|
|
129
123
|
reflection.setFlag(index_1.ReflectionFlag.Static);
|
|
@@ -32,6 +32,8 @@ export declare class Converter extends ChildableComponent<Application, Converter
|
|
|
32
32
|
validation: ValidationOptions;
|
|
33
33
|
/** @internal */
|
|
34
34
|
externalSymbolLinkMappings: Record<string, Record<string, string>>;
|
|
35
|
+
/** @internal */
|
|
36
|
+
useTsLinkResolution: boolean;
|
|
35
37
|
private _config?;
|
|
36
38
|
private _externalSymbolResolvers;
|
|
37
39
|
get config(): CommentParserConfig;
|
|
@@ -123,10 +123,10 @@ let Converter = Converter_1 = class Converter extends component_1.ChildableCompo
|
|
|
123
123
|
}
|
|
124
124
|
resolveLinks(comment, owner) {
|
|
125
125
|
if (comment instanceof index_1.Comment) {
|
|
126
|
-
(0, linkResolver_1.resolveLinks)(comment, owner, (ref, part, refl) => this.resolveExternalLink(ref, part, refl));
|
|
126
|
+
(0, linkResolver_1.resolveLinks)(comment, owner, (ref, part, refl) => this.resolveExternalLink(ref, part, refl), this.useTsLinkResolution);
|
|
127
127
|
}
|
|
128
128
|
else {
|
|
129
|
-
return (0, linkResolver_1.resolvePartLinks)(owner, comment, (ref, part, refl) => this.resolveExternalLink(ref, part, refl));
|
|
129
|
+
return (0, linkResolver_1.resolvePartLinks)(owner, comment, (ref, part, refl) => this.resolveExternalLink(ref, part, refl), this.useTsLinkResolution);
|
|
130
130
|
}
|
|
131
131
|
}
|
|
132
132
|
/**
|
|
@@ -166,7 +166,7 @@ let Converter = Converter_1 = class Converter extends component_1.ChildableCompo
|
|
|
166
166
|
context.project.registerReflection(context.project, symbol);
|
|
167
167
|
context.project.comment =
|
|
168
168
|
symbol &&
|
|
169
|
-
(0, comments_1.getComment)(symbol, context.project.kind, this.config, this.application.logger, this.commentStyle);
|
|
169
|
+
(0, comments_1.getComment)(symbol, context.project.kind, this.config, this.application.logger, this.commentStyle, context.checker);
|
|
170
170
|
context.trigger(Converter_1.EVENT_CREATE_DECLARATION, context.project);
|
|
171
171
|
moduleContext = context;
|
|
172
172
|
}
|
|
@@ -334,6 +334,9 @@ __decorate([
|
|
|
334
334
|
__decorate([
|
|
335
335
|
(0, utils_1.BindOption)("externalSymbolLinkMappings")
|
|
336
336
|
], Converter.prototype, "externalSymbolLinkMappings", void 0);
|
|
337
|
+
__decorate([
|
|
338
|
+
(0, utils_1.BindOption)("useTsLinkResolution")
|
|
339
|
+
], Converter.prototype, "useTsLinkResolution", void 0);
|
|
337
340
|
Converter = Converter_1 = __decorate([
|
|
338
341
|
(0, component_1.Component)({
|
|
339
342
|
name: "converter",
|