@fuzdev/fuz_ui 0.194.0 → 0.195.0
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/dist/DeclarationDetail.svelte +139 -64
- package/dist/DeclarationDetail.svelte.d.ts +9 -0
- package/dist/DeclarationDetail.svelte.d.ts.map +1 -1
- package/dist/LibraryDetail.svelte +14 -10
- package/dist/LibraryDetail.svelte.d.ts +7 -0
- package/dist/LibraryDetail.svelte.d.ts.map +1 -1
- package/dist/declaration.svelte.d.ts +233 -25
- package/dist/declaration.svelte.d.ts.map +1 -1
- package/dist/declaration.svelte.js +71 -23
- package/dist/library.svelte.js +1 -1
- package/dist/library_gen.d.ts +24 -17
- package/dist/library_gen.d.ts.map +1 -1
- package/dist/library_gen.js +52 -32
- package/dist/library_output.d.ts +5 -4
- package/dist/library_output.d.ts.map +1 -1
- package/dist/library_output.js +11 -8
- package/dist/module.svelte.d.ts +21 -7
- package/dist/module.svelte.d.ts.map +1 -1
- package/dist/module.svelte.js +26 -11
- package/dist/tsdoc_mdz.d.ts +6 -1
- package/dist/tsdoc_mdz.d.ts.map +1 -1
- package/dist/tsdoc_mdz.js +23 -2
- package/package.json +10 -8
- package/src/lib/declaration.svelte.ts +90 -35
- package/src/lib/library.svelte.ts +1 -1
- package/src/lib/library_gen.ts +65 -42
- package/src/lib/library_output.ts +11 -8
- package/src/lib/module.svelte.ts +29 -16
- package/src/lib/tsdoc_mdz.ts +25 -2
- package/dist/analysis_context.d.ts +0 -199
- package/dist/analysis_context.d.ts.map +0 -1
- package/dist/analysis_context.js +0 -138
- package/dist/library_analysis.d.ts +0 -112
- package/dist/library_analysis.d.ts.map +0 -1
- package/dist/library_analysis.js +0 -106
- package/dist/library_generate.d.ts +0 -94
- package/dist/library_generate.d.ts.map +0 -1
- package/dist/library_generate.js +0 -147
- package/dist/library_pipeline.d.ts +0 -113
- package/dist/library_pipeline.d.ts.map +0 -1
- package/dist/library_pipeline.js +0 -160
- package/dist/module_helpers.d.ts +0 -334
- package/dist/module_helpers.d.ts.map +0 -1
- package/dist/module_helpers.js +0 -317
- package/dist/svelte_helpers.d.ts +0 -92
- package/dist/svelte_helpers.d.ts.map +0 -1
- package/dist/svelte_helpers.js +0 -367
- package/dist/ts_helpers.d.ts +0 -181
- package/dist/ts_helpers.d.ts.map +0 -1
- package/dist/ts_helpers.js +0 -674
- package/dist/tsdoc_helpers.d.ts +0 -119
- package/dist/tsdoc_helpers.d.ts.map +0 -1
- package/dist/tsdoc_helpers.js +0 -207
- package/src/lib/analysis_context.ts +0 -254
- package/src/lib/library_analysis.ts +0 -168
- package/src/lib/library_generate.ts +0 -215
- package/src/lib/library_pipeline.ts +0 -221
- package/src/lib/module_helpers.ts +0 -501
- package/src/lib/svelte_helpers.ts +0 -539
- package/src/lib/ts_helpers.ts +0 -862
- package/src/lib/tsdoc_helpers.ts +0 -246
package/dist/tsdoc_helpers.d.ts
DELETED
|
@@ -1,119 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* TSDoc/JSDoc parsing helpers using the TypeScript Compiler API.
|
|
3
|
-
*
|
|
4
|
-
* Provides `tsdoc_parse()` for extracting JSDoc/TSDoc from TypeScript nodes.
|
|
5
|
-
* Primarily designed for build-time code generation but can be used at runtime.
|
|
6
|
-
*
|
|
7
|
-
* ## Design
|
|
8
|
-
*
|
|
9
|
-
* Pure extraction approach: extracts documentation as-is with minimal transformation,
|
|
10
|
-
* preserving source intent. Works around TypeScript Compiler API quirks where needed.
|
|
11
|
-
*
|
|
12
|
-
* Supports both regular TypeScript and Svelte components (via svelte2tsx output).
|
|
13
|
-
*
|
|
14
|
-
* ## Tag support
|
|
15
|
-
*
|
|
16
|
-
* Supports a subset of standard TSDoc tags:
|
|
17
|
-
* `@param`, `@returns`, `@throws`, `@example`, `@deprecated`, `@see`, `@since`, `@nodocs`.
|
|
18
|
-
*
|
|
19
|
-
* The `@nodocs` tag excludes exports from documentation and flat namespace validation.
|
|
20
|
-
* The declaration is still exported and usable, just not documented.
|
|
21
|
-
*
|
|
22
|
-
* Also supports `@mutates` (non-standard) for documenting mutations to parameters or external state.
|
|
23
|
-
* Use format: `@mutates paramName - description of mutation`.
|
|
24
|
-
*
|
|
25
|
-
* Only `@returns` is supported (not `@return`).
|
|
26
|
-
*
|
|
27
|
-
* The `@see` tag supports multiple formats: plain URLs (`https://...`), `{@link}` syntax, and module names.
|
|
28
|
-
* Relative/absolute path support in `@see` is TBD.
|
|
29
|
-
*
|
|
30
|
-
* ## Behavioral notes
|
|
31
|
-
*
|
|
32
|
-
* Due to TS Compiler API limitations:
|
|
33
|
-
* - `@param` and `@mutates` descriptions have leading `- ` stripped for visual consistency
|
|
34
|
-
* (TSDoc spec uses `@param name - description` but the separator is aesthetic)
|
|
35
|
-
* - `@throws` tags have `{Type}` stripped by TS API; fallback regex extracts first word as error type
|
|
36
|
-
* - TS API strips URL protocols from `@see` tag text; we use `getText()` to preserve original format including `{@link}` syntax
|
|
37
|
-
*
|
|
38
|
-
* All functions are prefixed with `tsdoc_` for clarity.
|
|
39
|
-
*
|
|
40
|
-
* @module
|
|
41
|
-
*/
|
|
42
|
-
import ts from 'typescript';
|
|
43
|
-
import type { DeclarationJson } from '@fuzdev/fuz_util/source_json.js';
|
|
44
|
-
/**
|
|
45
|
-
* Parsed JSDoc/TSDoc comment with structured metadata.
|
|
46
|
-
*/
|
|
47
|
-
export interface TsdocParsedComment {
|
|
48
|
-
/** Comment text (excluding comment markers) */
|
|
49
|
-
text: string;
|
|
50
|
-
/** Parameter descriptions mapped by parameter name */
|
|
51
|
-
params: Map<string, string>;
|
|
52
|
-
/** Return value description from `@returns` */
|
|
53
|
-
returns?: string;
|
|
54
|
-
/** Thrown errors from `@throws` */
|
|
55
|
-
throws?: Array<{
|
|
56
|
-
type?: string;
|
|
57
|
-
description: string;
|
|
58
|
-
}>;
|
|
59
|
-
/** Code examples from `@example` */
|
|
60
|
-
examples?: Array<string>;
|
|
61
|
-
/** Deprecation message from `@deprecated` */
|
|
62
|
-
deprecated_message?: string;
|
|
63
|
-
/** Related references from `@see` */
|
|
64
|
-
see_also?: Array<string>;
|
|
65
|
-
/** Version information from `@since` */
|
|
66
|
-
since?: string;
|
|
67
|
-
/** Mutation documentation from `@mutates` (non-standard) */
|
|
68
|
-
mutates?: Array<string>;
|
|
69
|
-
/** Whether to exclude from documentation. From `@nodocs` tag. */
|
|
70
|
-
nodocs?: boolean;
|
|
71
|
-
}
|
|
72
|
-
/**
|
|
73
|
-
* Parse JSDoc comment from a TypeScript node.
|
|
74
|
-
*
|
|
75
|
-
* Extracts and parses all JSDoc tags including:
|
|
76
|
-
*
|
|
77
|
-
* - `@param` - parameter descriptions
|
|
78
|
-
* - `@returns` - return value description
|
|
79
|
-
* - `@throws` - error documentation
|
|
80
|
-
* - `@example` - code examples
|
|
81
|
-
* - `@deprecated` - deprecation warnings
|
|
82
|
-
* - `@see` - related references
|
|
83
|
-
* - `@since` - version information
|
|
84
|
-
* - `@mutates` - mutation documentation (non-standard)
|
|
85
|
-
*
|
|
86
|
-
* @param node - the TypeScript node to extract JSDoc from
|
|
87
|
-
* @param source_file - source file (used for extracting full ` @see` tag text)
|
|
88
|
-
*/
|
|
89
|
-
export declare const tsdoc_parse: (node: ts.Node, source_file: ts.SourceFile) => TsdocParsedComment | undefined;
|
|
90
|
-
/**
|
|
91
|
-
* Apply parsed TSDoc metadata to a declaration.
|
|
92
|
-
*
|
|
93
|
-
* Consolidates the common pattern of assigning TSDoc fields to declarations,
|
|
94
|
-
* with conditional assignment for array fields (only if non-empty).
|
|
95
|
-
*
|
|
96
|
-
* @param declaration - declaration object to update
|
|
97
|
-
* @param tsdoc - parsed TSDoc comment (if available)
|
|
98
|
-
* @mutates declaration - adds doc_comment, deprecated_message, examples, see_also, throws, since fields
|
|
99
|
-
*/
|
|
100
|
-
export declare const tsdoc_apply_to_declaration: (declaration: DeclarationJson, tsdoc: TsdocParsedComment | undefined) => void;
|
|
101
|
-
/**
|
|
102
|
-
* Concatenates a JSDoc comment (string or node array) into plain text, preserving `{@link ...}`.
|
|
103
|
-
*
|
|
104
|
-
* `JSDocLink` / `JSDocLinkCode` / `JSDocLinkPlain` nodes have empty `.text` — the identifier
|
|
105
|
-
* lives on `.name`, not `.text`. Using `.text` alone silently drops link content; we fall back
|
|
106
|
-
* to the source-text representation for link nodes so `{@link Foo}` survives intact for downstream
|
|
107
|
-
* renderers (see `tsdoc_mdz.ts`).
|
|
108
|
-
*/
|
|
109
|
-
export declare const tsdoc_comment_to_text: (comment: string | ts.NodeArray<ts.JSDocComment>, source_file: ts.SourceFile) => string;
|
|
110
|
-
/**
|
|
111
|
-
* Clean raw JSDoc comment text by removing comment markers and leading asterisks.
|
|
112
|
-
*
|
|
113
|
-
* Transforms `/** ... *\/` style comments into clean text.
|
|
114
|
-
*
|
|
115
|
-
* @param comment_text - the raw comment text including `/**` and `*\/` markers
|
|
116
|
-
* @returns cleaned comment text, or undefined if empty after cleaning
|
|
117
|
-
*/
|
|
118
|
-
export declare const tsdoc_clean_comment: (comment_text: string) => string | undefined;
|
|
119
|
-
//# sourceMappingURL=tsdoc_helpers.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"tsdoc_helpers.d.ts","sourceRoot":"../src/lib/","sources":["../src/lib/tsdoc_helpers.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAwCG;AAEH,OAAO,EAAE,MAAM,YAAY,CAAC;AAC5B,OAAO,KAAK,EAAC,eAAe,EAAC,MAAM,iCAAiC,CAAC;AAErE;;GAEG;AACH,MAAM,WAAW,kBAAkB;IAClC,+CAA+C;IAC/C,IAAI,EAAE,MAAM,CAAC;IACb,sDAAsD;IACtD,MAAM,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAC5B,+CAA+C;IAC/C,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,mCAAmC;IACnC,MAAM,CAAC,EAAE,KAAK,CAAC;QAAC,IAAI,CAAC,EAAE,MAAM,CAAC;QAAC,WAAW,EAAE,MAAM,CAAA;KAAC,CAAC,CAAC;IACrD,oCAAoC;IACpC,QAAQ,CAAC,EAAE,KAAK,CAAC,MAAM,CAAC,CAAC;IACzB,6CAA6C;IAC7C,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,qCAAqC;IACrC,QAAQ,CAAC,EAAE,KAAK,CAAC,MAAM,CAAC,CAAC;IACzB,wCAAwC;IACxC,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,4DAA4D;IAC5D,OAAO,CAAC,EAAE,KAAK,CAAC,MAAM,CAAC,CAAC;IACxB,iEAAiE;IACjE,MAAM,CAAC,EAAE,OAAO,CAAC;CACjB;AAED;;;;;;;;;;;;;;;;GAgBG;AACH,eAAO,MAAM,WAAW,GACvB,MAAM,EAAE,CAAC,IAAI,EACb,aAAa,EAAE,CAAC,UAAU,KACxB,kBAAkB,GAAG,SAoFvB,CAAC;AAEF;;;;;;;;;GASG;AACH,eAAO,MAAM,0BAA0B,GACtC,aAAa,eAAe,EAC5B,OAAO,kBAAkB,GAAG,SAAS,KACnC,IAmBF,CAAC;AAEF;;;;;;;GAOG;AACH,eAAO,MAAM,qBAAqB,GACjC,SAAS,MAAM,GAAG,EAAE,CAAC,SAAS,CAAC,EAAE,CAAC,YAAY,CAAC,EAC/C,aAAa,EAAE,CAAC,UAAU,KACxB,MAGF,CAAC;AAEF;;;;;;;GAOG;AACH,eAAO,MAAM,mBAAmB,GAAI,cAAc,MAAM,KAAG,MAAM,GAAG,SAUnE,CAAC"}
|
package/dist/tsdoc_helpers.js
DELETED
|
@@ -1,207 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* TSDoc/JSDoc parsing helpers using the TypeScript Compiler API.
|
|
3
|
-
*
|
|
4
|
-
* Provides `tsdoc_parse()` for extracting JSDoc/TSDoc from TypeScript nodes.
|
|
5
|
-
* Primarily designed for build-time code generation but can be used at runtime.
|
|
6
|
-
*
|
|
7
|
-
* ## Design
|
|
8
|
-
*
|
|
9
|
-
* Pure extraction approach: extracts documentation as-is with minimal transformation,
|
|
10
|
-
* preserving source intent. Works around TypeScript Compiler API quirks where needed.
|
|
11
|
-
*
|
|
12
|
-
* Supports both regular TypeScript and Svelte components (via svelte2tsx output).
|
|
13
|
-
*
|
|
14
|
-
* ## Tag support
|
|
15
|
-
*
|
|
16
|
-
* Supports a subset of standard TSDoc tags:
|
|
17
|
-
* `@param`, `@returns`, `@throws`, `@example`, `@deprecated`, `@see`, `@since`, `@nodocs`.
|
|
18
|
-
*
|
|
19
|
-
* The `@nodocs` tag excludes exports from documentation and flat namespace validation.
|
|
20
|
-
* The declaration is still exported and usable, just not documented.
|
|
21
|
-
*
|
|
22
|
-
* Also supports `@mutates` (non-standard) for documenting mutations to parameters or external state.
|
|
23
|
-
* Use format: `@mutates paramName - description of mutation`.
|
|
24
|
-
*
|
|
25
|
-
* Only `@returns` is supported (not `@return`).
|
|
26
|
-
*
|
|
27
|
-
* The `@see` tag supports multiple formats: plain URLs (`https://...`), `{@link}` syntax, and module names.
|
|
28
|
-
* Relative/absolute path support in `@see` is TBD.
|
|
29
|
-
*
|
|
30
|
-
* ## Behavioral notes
|
|
31
|
-
*
|
|
32
|
-
* Due to TS Compiler API limitations:
|
|
33
|
-
* - `@param` and `@mutates` descriptions have leading `- ` stripped for visual consistency
|
|
34
|
-
* (TSDoc spec uses `@param name - description` but the separator is aesthetic)
|
|
35
|
-
* - `@throws` tags have `{Type}` stripped by TS API; fallback regex extracts first word as error type
|
|
36
|
-
* - TS API strips URL protocols from `@see` tag text; we use `getText()` to preserve original format including `{@link}` syntax
|
|
37
|
-
*
|
|
38
|
-
* All functions are prefixed with `tsdoc_` for clarity.
|
|
39
|
-
*
|
|
40
|
-
* @module
|
|
41
|
-
*/
|
|
42
|
-
import ts from 'typescript';
|
|
43
|
-
/**
|
|
44
|
-
* Parse JSDoc comment from a TypeScript node.
|
|
45
|
-
*
|
|
46
|
-
* Extracts and parses all JSDoc tags including:
|
|
47
|
-
*
|
|
48
|
-
* - `@param` - parameter descriptions
|
|
49
|
-
* - `@returns` - return value description
|
|
50
|
-
* - `@throws` - error documentation
|
|
51
|
-
* - `@example` - code examples
|
|
52
|
-
* - `@deprecated` - deprecation warnings
|
|
53
|
-
* - `@see` - related references
|
|
54
|
-
* - `@since` - version information
|
|
55
|
-
* - `@mutates` - mutation documentation (non-standard)
|
|
56
|
-
*
|
|
57
|
-
* @param node - the TypeScript node to extract JSDoc from
|
|
58
|
-
* @param source_file - source file (used for extracting full ` @see` tag text)
|
|
59
|
-
*/
|
|
60
|
-
export const tsdoc_parse = (node, source_file) => {
|
|
61
|
-
const tsdoc_comments = ts.getJSDocCommentsAndTags(node);
|
|
62
|
-
if (tsdoc_comments.length === 0)
|
|
63
|
-
return undefined;
|
|
64
|
-
let full_text = '';
|
|
65
|
-
const params = new Map();
|
|
66
|
-
let returns;
|
|
67
|
-
const throws = [];
|
|
68
|
-
const examples = [];
|
|
69
|
-
let deprecated_message;
|
|
70
|
-
const see_also = [];
|
|
71
|
-
let since;
|
|
72
|
-
const mutates = [];
|
|
73
|
-
let nodocs = false;
|
|
74
|
-
// Extract main comment text
|
|
75
|
-
for (const comment of tsdoc_comments) {
|
|
76
|
-
if (ts.isJSDoc(comment) && comment.comment) {
|
|
77
|
-
full_text += tsdoc_comment_to_text(comment.comment, source_file) + '\n';
|
|
78
|
-
}
|
|
79
|
-
}
|
|
80
|
-
// Extract tags
|
|
81
|
-
const tags = ts.getJSDocTags(node);
|
|
82
|
-
for (const tag of tags) {
|
|
83
|
-
const tag_text = tag.comment ? tsdoc_comment_to_text(tag.comment, source_file) : undefined;
|
|
84
|
-
const tag_name = tag.tagName.text;
|
|
85
|
-
if (tag_name === 'param' && ts.isJSDocParameterTag(tag)) {
|
|
86
|
-
// Extract parameter name and description
|
|
87
|
-
const param_name = ts.isIdentifier(tag.name) ? tag.name.text : tag.name.getText();
|
|
88
|
-
if (param_name && tag_text) {
|
|
89
|
-
params.set(param_name, tag_text.trim().replace(/^-\s+/, ''));
|
|
90
|
-
}
|
|
91
|
-
}
|
|
92
|
-
else if (tag_name === 'returns' && tag_text) {
|
|
93
|
-
returns = tag_text.trim();
|
|
94
|
-
}
|
|
95
|
-
else if (tag_name === 'throws' && tag_text) {
|
|
96
|
-
// Try to extract error type and description
|
|
97
|
-
const match = /^\{?(\w+)\}?\s+(.+)/.exec(tag_text);
|
|
98
|
-
if (match) {
|
|
99
|
-
throws.push({ type: match[1], description: match[2].trim() });
|
|
100
|
-
}
|
|
101
|
-
else {
|
|
102
|
-
throws.push({ description: tag_text.trim() });
|
|
103
|
-
}
|
|
104
|
-
}
|
|
105
|
-
else if (tag_name === 'example' && tag_text) {
|
|
106
|
-
examples.push(tag_text.trim());
|
|
107
|
-
}
|
|
108
|
-
else if (tag_name === 'deprecated' && tag_text) {
|
|
109
|
-
deprecated_message = tag_text.trim();
|
|
110
|
-
}
|
|
111
|
-
else if (tag_name === 'see') {
|
|
112
|
-
// The TS API strips 'https' from URLs in @see tags, so get full text from source
|
|
113
|
-
const full_tag_text = tag.getText(source_file);
|
|
114
|
-
// Extract content after @see, handling JSDoc formatting artifacts
|
|
115
|
-
const see_content = full_tag_text
|
|
116
|
-
.replace(/^@see\s+/, '') // remove @see prefix
|
|
117
|
-
.replace(/\n\s*\*\s*/g, ' ') // remove JSDoc line continuations
|
|
118
|
-
.replace(/\s*\*\s*$/, '') // remove trailing asterisk artifacts
|
|
119
|
-
.trim();
|
|
120
|
-
if (see_content) {
|
|
121
|
-
see_also.push(see_content);
|
|
122
|
-
}
|
|
123
|
-
}
|
|
124
|
-
else if (tag_name === 'since' && tag_text) {
|
|
125
|
-
since = tag_text.trim();
|
|
126
|
-
}
|
|
127
|
-
else if (tag_name === 'mutates' && tag_text) {
|
|
128
|
-
mutates.push(tag_text.trim().replace(/^-\s+/, ''));
|
|
129
|
-
}
|
|
130
|
-
else if (tag_name === 'nodocs') {
|
|
131
|
-
nodocs = true;
|
|
132
|
-
}
|
|
133
|
-
}
|
|
134
|
-
full_text = full_text.trim();
|
|
135
|
-
return {
|
|
136
|
-
text: full_text,
|
|
137
|
-
params,
|
|
138
|
-
returns,
|
|
139
|
-
...(throws.length && { throws }),
|
|
140
|
-
...(examples.length && { examples }),
|
|
141
|
-
deprecated_message,
|
|
142
|
-
...(see_also.length && { see_also }),
|
|
143
|
-
since,
|
|
144
|
-
...(mutates.length && { mutates }),
|
|
145
|
-
...(nodocs && { nodocs }),
|
|
146
|
-
};
|
|
147
|
-
};
|
|
148
|
-
/**
|
|
149
|
-
* Apply parsed TSDoc metadata to a declaration.
|
|
150
|
-
*
|
|
151
|
-
* Consolidates the common pattern of assigning TSDoc fields to declarations,
|
|
152
|
-
* with conditional assignment for array fields (only if non-empty).
|
|
153
|
-
*
|
|
154
|
-
* @param declaration - declaration object to update
|
|
155
|
-
* @param tsdoc - parsed TSDoc comment (if available)
|
|
156
|
-
* @mutates declaration - adds doc_comment, deprecated_message, examples, see_also, throws, since fields
|
|
157
|
-
*/
|
|
158
|
-
export const tsdoc_apply_to_declaration = (declaration, tsdoc) => {
|
|
159
|
-
if (!tsdoc)
|
|
160
|
-
return;
|
|
161
|
-
declaration.doc_comment = tsdoc.text;
|
|
162
|
-
declaration.deprecated_message = tsdoc.deprecated_message;
|
|
163
|
-
// Only assign arrays if they have content
|
|
164
|
-
if (tsdoc.examples?.length) {
|
|
165
|
-
declaration.examples = tsdoc.examples;
|
|
166
|
-
}
|
|
167
|
-
if (tsdoc.see_also?.length) {
|
|
168
|
-
declaration.see_also = tsdoc.see_also;
|
|
169
|
-
}
|
|
170
|
-
if (tsdoc.throws?.length) {
|
|
171
|
-
declaration.throws = tsdoc.throws;
|
|
172
|
-
}
|
|
173
|
-
if (tsdoc.since) {
|
|
174
|
-
declaration.since = tsdoc.since;
|
|
175
|
-
}
|
|
176
|
-
};
|
|
177
|
-
/**
|
|
178
|
-
* Concatenates a JSDoc comment (string or node array) into plain text, preserving `{@link ...}`.
|
|
179
|
-
*
|
|
180
|
-
* `JSDocLink` / `JSDocLinkCode` / `JSDocLinkPlain` nodes have empty `.text` — the identifier
|
|
181
|
-
* lives on `.name`, not `.text`. Using `.text` alone silently drops link content; we fall back
|
|
182
|
-
* to the source-text representation for link nodes so `{@link Foo}` survives intact for downstream
|
|
183
|
-
* renderers (see `tsdoc_mdz.ts`).
|
|
184
|
-
*/
|
|
185
|
-
export const tsdoc_comment_to_text = (comment, source_file) => {
|
|
186
|
-
if (typeof comment === 'string')
|
|
187
|
-
return comment;
|
|
188
|
-
return comment.map((c) => (ts.isJSDocLinkLike(c) ? c.getText(source_file) : c.text)).join('');
|
|
189
|
-
};
|
|
190
|
-
/**
|
|
191
|
-
* Clean raw JSDoc comment text by removing comment markers and leading asterisks.
|
|
192
|
-
*
|
|
193
|
-
* Transforms `/** ... *\/` style comments into clean text.
|
|
194
|
-
*
|
|
195
|
-
* @param comment_text - the raw comment text including `/**` and `*\/` markers
|
|
196
|
-
* @returns cleaned comment text, or undefined if empty after cleaning
|
|
197
|
-
*/
|
|
198
|
-
export const tsdoc_clean_comment = (comment_text) => {
|
|
199
|
-
const text = comment_text
|
|
200
|
-
.replace(/^\/\*\*/, '')
|
|
201
|
-
.replace(/\*\/$/, '')
|
|
202
|
-
.split('\n')
|
|
203
|
-
.map((line) => line.replace(/^\s*\*\s?/, ''))
|
|
204
|
-
.join('\n')
|
|
205
|
-
.trim();
|
|
206
|
-
return text || undefined;
|
|
207
|
-
};
|
|
@@ -1,254 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Diagnostic collection for source analysis.
|
|
3
|
-
*
|
|
4
|
-
* Provides structured error/warning collection during TypeScript and Svelte
|
|
5
|
-
* analysis, replacing silent catch blocks with actionable diagnostics.
|
|
6
|
-
*
|
|
7
|
-
* ## Error Handling Contract
|
|
8
|
-
*
|
|
9
|
-
* Analysis functions follow a two-tier error model:
|
|
10
|
-
*
|
|
11
|
-
* **Accumulated (non-fatal)** - Collected in `AnalysisContext`, analysis continues:
|
|
12
|
-
* - Type resolution failures (complex generics, circular refs)
|
|
13
|
-
* - Missing or unparseable JSDoc
|
|
14
|
-
* - Individual member/prop extraction failures
|
|
15
|
-
* - The return value is still valid but may have partial data
|
|
16
|
-
*
|
|
17
|
-
* **Thrown (fatal)** - Analysis cannot continue for this file:
|
|
18
|
-
* - File not found or unreadable
|
|
19
|
-
* - Syntax errors preventing parsing
|
|
20
|
-
* - svelte2tsx transformation failures
|
|
21
|
-
* - Svelte version incompatibility
|
|
22
|
-
*
|
|
23
|
-
* ## Usage Pattern
|
|
24
|
-
*
|
|
25
|
-
* ```ts
|
|
26
|
-
* const ctx = new AnalysisContext();
|
|
27
|
-
* const results = files.map(f => {
|
|
28
|
-
* try {
|
|
29
|
-
* return library_analyze_module(f, program, options, ctx);
|
|
30
|
-
* } catch (e) {
|
|
31
|
-
* // Fatal error - log and skip this file
|
|
32
|
-
* console.error(`Failed to analyze ${f.id}: ${e}`);
|
|
33
|
-
* return null;
|
|
34
|
-
* }
|
|
35
|
-
* });
|
|
36
|
-
*
|
|
37
|
-
* // Results are valid even with accumulated errors
|
|
38
|
-
* // Check ctx for diagnostics to display to user
|
|
39
|
-
* if (ctx.has_errors()) {
|
|
40
|
-
* for (const err of ctx.errors()) {
|
|
41
|
-
* console.error(format_diagnostic(err));
|
|
42
|
-
* }
|
|
43
|
-
* }
|
|
44
|
-
* ```
|
|
45
|
-
*
|
|
46
|
-
* @example
|
|
47
|
-
* ```ts
|
|
48
|
-
* const ctx = new AnalysisContext();
|
|
49
|
-
* // ... analysis functions add diagnostics via ctx.add(...)
|
|
50
|
-
* if (ctx.has_errors()) {
|
|
51
|
-
* for (const err of ctx.errors()) {
|
|
52
|
-
* console.error(`${err.file}:${err.line}: ${err.message}`);
|
|
53
|
-
* }
|
|
54
|
-
* }
|
|
55
|
-
* ```
|
|
56
|
-
*
|
|
57
|
-
* @module
|
|
58
|
-
*/
|
|
59
|
-
|
|
60
|
-
/**
|
|
61
|
-
* Diagnostic severity levels.
|
|
62
|
-
*
|
|
63
|
-
* - `error`: Analysis failed, declaration may be incomplete or missing data
|
|
64
|
-
* - `warning`: Partial success, something seems off but analysis continued
|
|
65
|
-
*/
|
|
66
|
-
export type DiagnosticSeverity = 'error' | 'warning';
|
|
67
|
-
|
|
68
|
-
/**
|
|
69
|
-
* Discriminant for diagnostic types.
|
|
70
|
-
*/
|
|
71
|
-
export type DiagnosticKind =
|
|
72
|
-
| 'type_extraction_failed'
|
|
73
|
-
| 'signature_analysis_failed'
|
|
74
|
-
| 'class_member_failed'
|
|
75
|
-
| 'svelte_prop_failed'
|
|
76
|
-
| 'module_skipped';
|
|
77
|
-
|
|
78
|
-
/**
|
|
79
|
-
* Base diagnostic fields shared by all diagnostic types.
|
|
80
|
-
*/
|
|
81
|
-
export interface BaseDiagnostic {
|
|
82
|
-
kind: DiagnosticKind;
|
|
83
|
-
/** File path relative to project root (display with './' prefix). */
|
|
84
|
-
file: string;
|
|
85
|
-
/** Line number (1-based), or null if location unavailable. */
|
|
86
|
-
line: number | null;
|
|
87
|
-
/** Column number (1-based), or null if location unavailable. */
|
|
88
|
-
column: number | null;
|
|
89
|
-
/** Human-readable description of the issue. */
|
|
90
|
-
message: string;
|
|
91
|
-
severity: DiagnosticSeverity;
|
|
92
|
-
}
|
|
93
|
-
|
|
94
|
-
/**
|
|
95
|
-
* Type extraction failed (e.g., complex or recursive types).
|
|
96
|
-
*/
|
|
97
|
-
export interface TypeExtractionDiagnostic extends BaseDiagnostic {
|
|
98
|
-
kind: 'type_extraction_failed';
|
|
99
|
-
/** Name of the symbol whose type couldn't be extracted. */
|
|
100
|
-
symbol_name: string;
|
|
101
|
-
}
|
|
102
|
-
|
|
103
|
-
/**
|
|
104
|
-
* Function/method signature analysis failed.
|
|
105
|
-
*/
|
|
106
|
-
export interface SignatureAnalysisDiagnostic extends BaseDiagnostic {
|
|
107
|
-
kind: 'signature_analysis_failed';
|
|
108
|
-
/** Name of the function or method. */
|
|
109
|
-
function_name: string;
|
|
110
|
-
}
|
|
111
|
-
|
|
112
|
-
/**
|
|
113
|
-
* Class member analysis failed.
|
|
114
|
-
*/
|
|
115
|
-
export interface ClassMemberDiagnostic extends BaseDiagnostic {
|
|
116
|
-
kind: 'class_member_failed';
|
|
117
|
-
/** Name of the class. */
|
|
118
|
-
class_name: string;
|
|
119
|
-
/** Name of the member that failed. */
|
|
120
|
-
member_name: string;
|
|
121
|
-
}
|
|
122
|
-
|
|
123
|
-
/**
|
|
124
|
-
* Svelte prop type resolution failed.
|
|
125
|
-
*/
|
|
126
|
-
export interface SveltePropDiagnostic extends BaseDiagnostic {
|
|
127
|
-
kind: 'svelte_prop_failed';
|
|
128
|
-
/** Name of the component. */
|
|
129
|
-
component_name: string;
|
|
130
|
-
/** Name of the prop. */
|
|
131
|
-
prop_name: string;
|
|
132
|
-
}
|
|
133
|
-
|
|
134
|
-
/**
|
|
135
|
-
* Module was skipped during analysis.
|
|
136
|
-
* Could be due to missing source file in program or no analyzer available.
|
|
137
|
-
*/
|
|
138
|
-
export interface ModuleSkippedDiagnostic extends BaseDiagnostic {
|
|
139
|
-
kind: 'module_skipped';
|
|
140
|
-
/** Reason the module was skipped. */
|
|
141
|
-
reason: 'not_in_program' | 'no_analyzer';
|
|
142
|
-
}
|
|
143
|
-
|
|
144
|
-
/**
|
|
145
|
-
* Union of all diagnostic types.
|
|
146
|
-
*/
|
|
147
|
-
export type Diagnostic =
|
|
148
|
-
| TypeExtractionDiagnostic
|
|
149
|
-
| SignatureAnalysisDiagnostic
|
|
150
|
-
| ClassMemberDiagnostic
|
|
151
|
-
| SveltePropDiagnostic
|
|
152
|
-
| ModuleSkippedDiagnostic;
|
|
153
|
-
|
|
154
|
-
/**
|
|
155
|
-
* Context for collecting diagnostics during source analysis.
|
|
156
|
-
*
|
|
157
|
-
* Thread an instance through analysis functions to collect errors and warnings
|
|
158
|
-
* without halting analysis. After analysis completes, check `has_errors()` and
|
|
159
|
-
* report collected diagnostics.
|
|
160
|
-
*
|
|
161
|
-
* @example
|
|
162
|
-
* ```ts
|
|
163
|
-
* const ctx = new AnalysisContext();
|
|
164
|
-
* ts_analyze_module_exports(source_file, checker, options, ctx);
|
|
165
|
-
* if (ctx.has_errors()) {
|
|
166
|
-
* console.error('Analysis completed with errors:');
|
|
167
|
-
* for (const d of ctx.errors()) {
|
|
168
|
-
* console.error(format_diagnostic(d));
|
|
169
|
-
* }
|
|
170
|
-
* }
|
|
171
|
-
* ```
|
|
172
|
-
*/
|
|
173
|
-
export class AnalysisContext {
|
|
174
|
-
readonly diagnostics: Array<Diagnostic> = [];
|
|
175
|
-
|
|
176
|
-
/**
|
|
177
|
-
* Add a `Diagnostic` to the collection.
|
|
178
|
-
*/
|
|
179
|
-
add(diagnostic: Diagnostic): void {
|
|
180
|
-
this.diagnostics.push(diagnostic);
|
|
181
|
-
}
|
|
182
|
-
|
|
183
|
-
/**
|
|
184
|
-
* Check if any errors were collected.
|
|
185
|
-
*/
|
|
186
|
-
has_errors(): boolean {
|
|
187
|
-
return this.diagnostics.some((d) => d.severity === 'error');
|
|
188
|
-
}
|
|
189
|
-
|
|
190
|
-
/**
|
|
191
|
-
* Check if any warnings were collected.
|
|
192
|
-
*/
|
|
193
|
-
has_warnings(): boolean {
|
|
194
|
-
return this.diagnostics.some((d) => d.severity === 'warning');
|
|
195
|
-
}
|
|
196
|
-
|
|
197
|
-
/**
|
|
198
|
-
* Get all error diagnostics.
|
|
199
|
-
*/
|
|
200
|
-
errors(): Array<Diagnostic> {
|
|
201
|
-
return this.diagnostics.filter((d) => d.severity === 'error');
|
|
202
|
-
}
|
|
203
|
-
|
|
204
|
-
/**
|
|
205
|
-
* Get all warning diagnostics.
|
|
206
|
-
*/
|
|
207
|
-
warnings(): Array<Diagnostic> {
|
|
208
|
-
return this.diagnostics.filter((d) => d.severity === 'warning');
|
|
209
|
-
}
|
|
210
|
-
|
|
211
|
-
/**
|
|
212
|
-
* Get diagnostics of a specific `DiagnosticKind`.
|
|
213
|
-
*/
|
|
214
|
-
by_kind<K extends DiagnosticKind>(kind: K): Array<Extract<Diagnostic, {kind: K}>> {
|
|
215
|
-
return this.diagnostics.filter((d) => d.kind === kind) as Array<Extract<Diagnostic, {kind: K}>>;
|
|
216
|
-
}
|
|
217
|
-
}
|
|
218
|
-
|
|
219
|
-
/**
|
|
220
|
-
* Options for formatting diagnostics.
|
|
221
|
-
*/
|
|
222
|
-
export interface FormatDiagnosticOptions {
|
|
223
|
-
/** Prefix for file path (default: './'). */
|
|
224
|
-
prefix?: string;
|
|
225
|
-
/** Base path to strip from absolute file paths (e.g., process.cwd()). */
|
|
226
|
-
strip_base?: string;
|
|
227
|
-
}
|
|
228
|
-
|
|
229
|
-
/**
|
|
230
|
-
* Format a diagnostic for display.
|
|
231
|
-
*
|
|
232
|
-
* @param diagnostic - the diagnostic to format
|
|
233
|
-
* @param options - formatting options
|
|
234
|
-
* @returns formatted string like './file.ts:10:5: error: message'
|
|
235
|
-
*/
|
|
236
|
-
export const format_diagnostic = (
|
|
237
|
-
diagnostic: Diagnostic,
|
|
238
|
-
options?: FormatDiagnosticOptions,
|
|
239
|
-
): string => {
|
|
240
|
-
const prefix = options?.prefix ?? './';
|
|
241
|
-
const strip_base = options?.strip_base;
|
|
242
|
-
|
|
243
|
-
let file = diagnostic.file;
|
|
244
|
-
if (strip_base && file.startsWith(strip_base)) {
|
|
245
|
-
file = file.slice(strip_base.length);
|
|
246
|
-
// Remove leading slash if present
|
|
247
|
-
if (file.startsWith('/')) file = file.slice(1);
|
|
248
|
-
}
|
|
249
|
-
|
|
250
|
-
const {line, column, severity, message} = diagnostic;
|
|
251
|
-
const location = line !== null ? (column !== null ? `${line}:${column}` : `${line}`) : '';
|
|
252
|
-
const file_part = location ? `${prefix}${file}:${location}` : `${prefix}${file}`;
|
|
253
|
-
return `${file_part}: ${severity}: ${message}`;
|
|
254
|
-
};
|