patram 0.11.0 → 0.12.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/bin/patram.js +4 -4
- package/lib/cli/commands/fields.js +0 -4
- package/lib/cli/commands/queries.js +10 -20
- package/lib/cli/commands/query.js +1 -8
- package/lib/cli/commands/refs.js +3 -10
- package/lib/cli/commands/show.js +1 -8
- package/lib/cli/help-metadata.js +71 -106
- package/lib/cli/main.js +10 -10
- package/lib/cli/parse-arguments-helpers.js +165 -59
- package/lib/cli/parse-arguments.js +4 -4
- package/lib/cli/render-help.js +2 -2
- package/lib/config/defaults.js +33 -25
- package/lib/config/load-patram-config.d.ts +8 -33
- package/lib/config/load-patram-config.js +9 -33
- package/lib/config/load-patram-config.types.d.ts +3 -40
- package/lib/config/manage-stored-queries-helpers.d.ts +4 -4
- package/lib/config/manage-stored-queries-helpers.js +91 -33
- package/lib/config/manage-stored-queries.d.ts +4 -4
- package/lib/config/manage-stored-queries.js +11 -5
- package/lib/config/patram-config.d.ts +34 -34
- package/lib/config/patram-config.js +3 -3
- package/lib/config/patram-config.types.d.ts +5 -11
- package/lib/config/resolve-patram-graph-config.d.ts +5 -1
- package/lib/config/resolve-patram-graph-config.js +3 -119
- package/lib/config/schema.d.ts +158 -269
- package/lib/config/schema.js +72 -210
- package/lib/config/validate-patram-config-value.js +6 -31
- package/lib/config/validation.d.ts +2 -12
- package/lib/config/validation.js +125 -483
- package/lib/find-close-match.d.ts +4 -1
- package/lib/graph/build-graph-identity.d.ts +1 -32
- package/lib/graph/build-graph-identity.js +5 -269
- package/lib/graph/build-graph.d.ts +13 -4
- package/lib/graph/build-graph.js +347 -488
- package/lib/graph/build-graph.types.d.ts +8 -9
- package/lib/graph/check-directive-metadata-helpers.d.ts +30 -0
- package/lib/graph/check-directive-metadata-helpers.js +126 -0
- package/lib/graph/check-directive-metadata.d.ts +8 -9
- package/lib/graph/check-directive-metadata.js +70 -561
- package/lib/graph/check-directive-path-target.d.ts +6 -13
- package/lib/graph/check-directive-path-target.js +26 -57
- package/lib/graph/check-directive-value.d.ts +1 -5
- package/lib/graph/check-directive-value.js +40 -180
- package/lib/graph/check-graph.d.ts +5 -5
- package/lib/graph/check-graph.js +8 -6
- package/lib/graph/document-node-identity.d.ts +23 -7
- package/lib/graph/document-node-identity.js +417 -160
- package/lib/graph/graph-node.d.ts +42 -0
- package/lib/graph/graph-node.js +83 -0
- package/lib/graph/inspect-reverse-references.js +16 -11
- package/lib/graph/load-project-graph.d.ts +7 -7
- package/lib/graph/load-project-graph.js +7 -7
- package/lib/graph/parse-where-clause.types.d.ts +3 -2
- package/lib/graph/query/cypher-reader.d.ts +59 -0
- package/lib/graph/query/cypher-reader.js +151 -0
- package/lib/graph/query/cypher-support.d.ts +79 -0
- package/lib/graph/query/cypher-support.js +213 -0
- package/lib/graph/query/cypher-tokenize.d.ts +13 -0
- package/lib/graph/query/cypher-tokenize.js +225 -0
- package/lib/graph/query/cypher.types.d.ts +43 -0
- package/lib/graph/query/execute.d.ts +7 -7
- package/lib/graph/query/execute.js +71 -33
- package/lib/graph/query/inspect.js +58 -24
- package/lib/graph/query/parse-cypher-patterns.d.ts +27 -0
- package/lib/graph/query/parse-cypher-patterns.js +382 -0
- package/lib/graph/query/parse-cypher.d.ts +7 -0
- package/lib/graph/query/parse-cypher.js +580 -0
- package/lib/graph/query/parse-query.d.ts +13 -0
- package/lib/graph/query/parse-query.js +97 -0
- package/lib/graph/query/resolve.js +77 -23
- package/lib/output/command-output.js +12 -5
- package/lib/output/compact-layout.js +221 -0
- package/lib/output/format-output-item-block.js +31 -1
- package/lib/output/format-output-metadata.js +16 -29
- package/lib/output/format-stored-query-block.js +95 -0
- package/lib/output/layout-incoming-references.js +101 -19
- package/lib/output/layout-stored-queries.js +23 -330
- package/lib/output/list-queries.js +1 -1
- package/lib/output/render-field-discovery.js +11 -2
- package/lib/output/render-output-view.js +9 -5
- package/lib/output/renderers/json.js +5 -26
- package/lib/output/renderers/plain.js +155 -35
- package/lib/output/renderers/rich.js +250 -36
- package/lib/output/resolved-link-layout.js +43 -0
- package/lib/output/rich-source/render.js +193 -35
- package/lib/output/show-document.js +25 -18
- package/lib/output/view-model/index.js +124 -103
- package/lib/parse/jsdoc/parse-jsdoc-blocks.js +1 -1
- package/lib/parse/jsdoc/parse-jsdoc-claims.js +12 -6
- package/lib/parse/markdown/parse-markdown-claims.js +99 -62
- package/lib/parse/markdown/parse-markdown-directives.d.ts +10 -6
- package/lib/parse/markdown/parse-markdown-directives.js +104 -18
- package/lib/parse/markdown/parse-markdown-prose.d.ts +27 -0
- package/lib/parse/markdown/parse-markdown-prose.js +243 -0
- package/lib/parse/parse-claims.d.ts +2 -6
- package/lib/parse/parse-claims.js +11 -53
- package/lib/parse/tagged-fenced/tagged-fenced-blocks.d.ts +4 -4
- package/lib/parse/tagged-fenced/tagged-fenced-blocks.js +4 -4
- package/lib/parse/yaml/parse-yaml-claims.js +4 -4
- package/lib/patram.d.ts +3 -5
- package/lib/patram.js +1 -1
- package/lib/scan/discover-fields.js +194 -55
- package/lib/scan/list-source-files.d.ts +4 -4
- package/lib/scan/list-source-files.js +4 -4
- package/package.json +1 -1
- package/lib/directive-validation-test-helpers.js +0 -87
- package/lib/graph/query/parse.d.ts +0 -75
- package/lib/graph/query/parse.js +0 -1064
- package/lib/output/derived-summary.js +0 -280
- package/lib/output/format-derived-summary-row.js +0 -9
|
@@ -1,19 +1,24 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @import { BuildGraphResult, GraphNode } from '../../graph/build-graph.types.ts';
|
|
3
|
-
* @import { DerivedSummaryEvaluator } from '../derived-summary.js';
|
|
4
3
|
* @import { PatramRepoConfig } from '../../config/load-patram-config.types.ts';
|
|
5
|
-
* @import {
|
|
4
|
+
* @import { OutputMetadataField, OutputNodeItem, OutputResolvedLinkItem, OutputResolvedLinkTarget, OutputStoredQueryItem, OutputView, RefsOutputView, ShowOutputView } from '../output-view.types.ts';
|
|
6
5
|
*/
|
|
7
6
|
/* eslint-disable max-lines */
|
|
8
7
|
|
|
9
8
|
import { resolveDocumentNodeId } from '../../graph/build-graph-identity.js';
|
|
9
|
+
import {
|
|
10
|
+
getGraphNodeClassName,
|
|
11
|
+
getGraphNodeId,
|
|
12
|
+
getGraphNodeMetadataValue,
|
|
13
|
+
getGraphNodePath,
|
|
14
|
+
} from '../../graph/graph-node.js';
|
|
10
15
|
|
|
11
16
|
/**
|
|
12
17
|
* Create a shared output view from one command result.
|
|
13
18
|
*
|
|
14
19
|
* @param {'query' | 'queries'} command_name
|
|
15
20
|
* @param {GraphNode[] | { name: string, where: string, description?: string }[]} command_items
|
|
16
|
-
* @param {{
|
|
21
|
+
* @param {{ hints?: string[], limit?: number, offset?: number, repo_config?: PatramRepoConfig, total_count?: number }=} command_options
|
|
17
22
|
* @returns {OutputView}
|
|
18
23
|
*/
|
|
19
24
|
export function createOutputView(command_name, command_items, command_options) {
|
|
@@ -37,7 +42,7 @@ export function createOutputView(command_name, command_items, command_options) {
|
|
|
37
42
|
* Create a shared output view for the show command.
|
|
38
43
|
*
|
|
39
44
|
* @param {{ incoming_summary: Record<string, number>, path: string, rendered_source: string, resolved_links: Array<{ label: string, reference: number, target: { kind?: string, path: string, status?: string, title: string } }>, source: string }} show_output
|
|
40
|
-
* @param {{
|
|
45
|
+
* @param {{ document_path_ids?: BuildGraphResult['document_path_ids'], graph_nodes?: BuildGraphResult['nodes'], repo_config?: PatramRepoConfig }=} command_options
|
|
41
46
|
* @returns {ShowOutputView}
|
|
42
47
|
*/
|
|
43
48
|
export function createShowOutputView(show_output, command_options = {}) {
|
|
@@ -62,7 +67,7 @@ export function createShowOutputView(show_output, command_options = {}) {
|
|
|
62
67
|
* Create a shared output view for the refs command.
|
|
63
68
|
*
|
|
64
69
|
* @param {{ incoming: Record<string, GraphNode[]>, node: GraphNode }} refs_output
|
|
65
|
-
* @param {{
|
|
70
|
+
* @param {{ repo_config?: PatramRepoConfig }=} command_options
|
|
66
71
|
* @returns {RefsOutputView}
|
|
67
72
|
*/
|
|
68
73
|
export function createRefsOutputView(refs_output, command_options = {}) {
|
|
@@ -74,8 +79,6 @@ export function createRefsOutputView(refs_output, command_options = {}) {
|
|
|
74
79
|
(graph_node) =>
|
|
75
80
|
createOutputNodeItem(
|
|
76
81
|
graph_node,
|
|
77
|
-
command_options.derived_summary_evaluator?.evaluate(graph_node) ??
|
|
78
|
-
null,
|
|
79
82
|
command_options.repo_config?.fields ?? {},
|
|
80
83
|
),
|
|
81
84
|
);
|
|
@@ -87,8 +90,6 @@ export function createRefsOutputView(refs_output, command_options = {}) {
|
|
|
87
90
|
incoming,
|
|
88
91
|
node: createOutputNodeItem(
|
|
89
92
|
refs_output.node,
|
|
90
|
-
command_options.derived_summary_evaluator?.evaluate(refs_output.node) ??
|
|
91
|
-
null,
|
|
92
93
|
command_options.repo_config?.fields ?? {},
|
|
93
94
|
),
|
|
94
95
|
summary: {
|
|
@@ -100,7 +101,7 @@ export function createRefsOutputView(refs_output, command_options = {}) {
|
|
|
100
101
|
|
|
101
102
|
/**
|
|
102
103
|
* @param {GraphNode[]} graph_nodes
|
|
103
|
-
* @param {{
|
|
104
|
+
* @param {{ hints?: string[], limit?: number, offset?: number, repo_config?: PatramRepoConfig, total_count?: number }=} command_options
|
|
104
105
|
* @returns {OutputView}
|
|
105
106
|
*/
|
|
106
107
|
function createQueryOutputView(graph_nodes, command_options = {}) {
|
|
@@ -110,11 +111,12 @@ function createQueryOutputView(graph_nodes, command_options = {}) {
|
|
|
110
111
|
command: 'query',
|
|
111
112
|
hints:
|
|
112
113
|
command_options.hints ??
|
|
113
|
-
(total_count === 0
|
|
114
|
+
(total_count === 0
|
|
115
|
+
? ['Try: patram query --cypher "MATCH (n:Task) RETURN n"']
|
|
116
|
+
: []),
|
|
114
117
|
items: graph_nodes.map((graph_node) =>
|
|
115
118
|
createOutputNodeItem(
|
|
116
119
|
graph_node,
|
|
117
|
-
command_options.derived_summary_evaluator?.evaluate(graph_node) ?? null,
|
|
118
120
|
command_options.repo_config?.fields ?? {},
|
|
119
121
|
),
|
|
120
122
|
),
|
|
@@ -166,11 +168,13 @@ function countIncomingReferenceItems(incoming) {
|
|
|
166
168
|
|
|
167
169
|
/**
|
|
168
170
|
* @param {GraphNode} graph_node
|
|
169
|
-
* @param {OutputDerivedSummary | null} derived_summary
|
|
170
171
|
* @param {NonNullable<PatramRepoConfig['fields']>} field_definitions
|
|
171
172
|
* @returns {OutputNodeItem}
|
|
172
173
|
*/
|
|
173
|
-
function createOutputNodeItem(graph_node,
|
|
174
|
+
function createOutputNodeItem(graph_node, field_definitions) {
|
|
175
|
+
const description = getScalarGraphNodeField(
|
|
176
|
+
getGraphNodeMetadataValue(graph_node, 'description'),
|
|
177
|
+
);
|
|
174
178
|
const title = getOutputNodeTitle(graph_node);
|
|
175
179
|
const path = getOutputNodePath(graph_node);
|
|
176
180
|
const node_class = getOutputNodeClass(graph_node);
|
|
@@ -179,12 +183,12 @@ function createOutputNodeItem(graph_node, derived_summary, field_definitions) {
|
|
|
179
183
|
|
|
180
184
|
if (!title || !node_class) {
|
|
181
185
|
throw new Error(
|
|
182
|
-
`Expected graph node "${graph_node
|
|
186
|
+
`Expected graph node "${getOutputNodeId(graph_node)}" to have a title and path.`,
|
|
183
187
|
);
|
|
184
188
|
}
|
|
185
189
|
|
|
186
|
-
|
|
187
|
-
|
|
190
|
+
/** @type {OutputNodeItem} */
|
|
191
|
+
const output_item = {
|
|
188
192
|
fields,
|
|
189
193
|
id: getOutputNodeId(graph_node),
|
|
190
194
|
kind: 'node',
|
|
@@ -193,21 +197,54 @@ function createOutputNodeItem(graph_node, derived_summary, field_definitions) {
|
|
|
193
197
|
title,
|
|
194
198
|
visible_fields,
|
|
195
199
|
};
|
|
200
|
+
|
|
201
|
+
if (description) {
|
|
202
|
+
output_item.description = description;
|
|
203
|
+
}
|
|
204
|
+
|
|
205
|
+
return output_item;
|
|
196
206
|
}
|
|
197
207
|
|
|
198
208
|
/**
|
|
199
209
|
* @param {{ kind?: string, path: string, status?: string, title: string }} target
|
|
200
210
|
* @param {NonNullable<PatramRepoConfig['fields']>} field_definitions
|
|
201
|
-
* @param {OutputDerivedSummary | null} derived_summary
|
|
202
211
|
* @param {GraphNode | undefined} graph_node
|
|
203
212
|
* @returns {OutputResolvedLinkTarget}
|
|
204
213
|
*/
|
|
205
|
-
function createResolvedLinkTarget(
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
)
|
|
214
|
+
function createResolvedLinkTarget(target, field_definitions, graph_node) {
|
|
215
|
+
const description = getScalarGraphNodeField(
|
|
216
|
+
graph_node
|
|
217
|
+
? getGraphNodeMetadataValue(graph_node, 'description')
|
|
218
|
+
: undefined,
|
|
219
|
+
);
|
|
220
|
+
const fields = collectResolvedLinkFields(
|
|
221
|
+
target,
|
|
222
|
+
field_definitions,
|
|
223
|
+
graph_node,
|
|
224
|
+
);
|
|
225
|
+
|
|
226
|
+
return {
|
|
227
|
+
description,
|
|
228
|
+
fields,
|
|
229
|
+
id: graph_node ? getOutputNodeId(graph_node) : `doc:${target.path}`,
|
|
230
|
+
kind: resolveResolvedLinkKind(target, graph_node),
|
|
231
|
+
path: resolveResolvedLinkPath(target, graph_node),
|
|
232
|
+
title: resolveResolvedLinkTitle(target, graph_node),
|
|
233
|
+
visible_fields: createVisibleOutputFields(fields, field_definitions),
|
|
234
|
+
};
|
|
235
|
+
}
|
|
236
|
+
|
|
237
|
+
/**
|
|
238
|
+
* @param {{ kind?: string, path: string, status?: string, title: string }} target
|
|
239
|
+
* @param {NonNullable<PatramRepoConfig['fields']>} field_definitions
|
|
240
|
+
* @param {GraphNode | undefined} graph_node
|
|
241
|
+
* @returns {Record<string, string | string[]>}
|
|
242
|
+
*/
|
|
243
|
+
function collectResolvedLinkFields(target, field_definitions, graph_node) {
|
|
244
|
+
if (graph_node) {
|
|
245
|
+
return collectOutputFields(graph_node, field_definitions);
|
|
246
|
+
}
|
|
247
|
+
|
|
211
248
|
/** @type {Record<string, string | string[]>} */
|
|
212
249
|
const fields = {};
|
|
213
250
|
|
|
@@ -215,18 +252,34 @@ function createResolvedLinkTarget(
|
|
|
215
252
|
fields.status = target.status;
|
|
216
253
|
}
|
|
217
254
|
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
255
|
+
return fields;
|
|
256
|
+
}
|
|
257
|
+
|
|
258
|
+
/**
|
|
259
|
+
* @param {{ kind?: string, path: string, status?: string, title: string }} target
|
|
260
|
+
* @param {GraphNode | undefined} graph_node
|
|
261
|
+
* @returns {string}
|
|
262
|
+
*/
|
|
263
|
+
function resolveResolvedLinkKind(target, graph_node) {
|
|
264
|
+
return getOutputNodeClass(graph_node) ?? target.kind ?? 'document';
|
|
265
|
+
}
|
|
266
|
+
|
|
267
|
+
/**
|
|
268
|
+
* @param {{ kind?: string, path: string, status?: string, title: string }} target
|
|
269
|
+
* @param {GraphNode | undefined} graph_node
|
|
270
|
+
* @returns {string}
|
|
271
|
+
*/
|
|
272
|
+
function resolveResolvedLinkPath(target, graph_node) {
|
|
273
|
+
return getOutputNodePath(graph_node) ?? target.path;
|
|
274
|
+
}
|
|
228
275
|
|
|
229
|
-
|
|
276
|
+
/**
|
|
277
|
+
* @param {{ kind?: string, path: string, status?: string, title: string }} target
|
|
278
|
+
* @param {GraphNode | undefined} graph_node
|
|
279
|
+
* @returns {string}
|
|
280
|
+
*/
|
|
281
|
+
function resolveResolvedLinkTitle(target, graph_node) {
|
|
282
|
+
return getOutputNodeTitle(graph_node) ?? target.title;
|
|
230
283
|
}
|
|
231
284
|
|
|
232
285
|
/**
|
|
@@ -242,32 +295,43 @@ function getScalarGraphNodeField(field_value) {
|
|
|
242
295
|
}
|
|
243
296
|
|
|
244
297
|
/**
|
|
245
|
-
* @param {GraphNode} graph_node
|
|
298
|
+
* @param {GraphNode | undefined} graph_node
|
|
246
299
|
* @returns {string | undefined}
|
|
247
300
|
*/
|
|
248
301
|
function getOutputNodeTitle(graph_node) {
|
|
302
|
+
if (!graph_node) {
|
|
303
|
+
return undefined;
|
|
304
|
+
}
|
|
305
|
+
|
|
249
306
|
return (
|
|
250
|
-
getScalarGraphNodeField(graph_node
|
|
251
|
-
getScalarGraphNodeField(graph_node.label) ??
|
|
307
|
+
getScalarGraphNodeField(getGraphNodeMetadataValue(graph_node, 'title')) ??
|
|
252
308
|
getOutputNodePath(graph_node) ??
|
|
253
309
|
getScalarGraphNodeField(graph_node.key)
|
|
254
310
|
);
|
|
255
311
|
}
|
|
256
312
|
|
|
257
313
|
/**
|
|
258
|
-
* @param {GraphNode} graph_node
|
|
314
|
+
* @param {GraphNode | undefined} graph_node
|
|
259
315
|
* @returns {string | undefined}
|
|
260
316
|
*/
|
|
261
317
|
function getOutputNodePath(graph_node) {
|
|
262
|
-
|
|
318
|
+
if (!graph_node) {
|
|
319
|
+
return undefined;
|
|
320
|
+
}
|
|
321
|
+
|
|
322
|
+
return getScalarGraphNodeField(getGraphNodePath(graph_node));
|
|
263
323
|
}
|
|
264
324
|
|
|
265
325
|
/**
|
|
266
|
-
* @param {GraphNode} graph_node
|
|
326
|
+
* @param {GraphNode | undefined} graph_node
|
|
267
327
|
* @returns {string | undefined}
|
|
268
328
|
*/
|
|
269
329
|
function getOutputNodeClass(graph_node) {
|
|
270
|
-
|
|
330
|
+
if (!graph_node) {
|
|
331
|
+
return undefined;
|
|
332
|
+
}
|
|
333
|
+
|
|
334
|
+
return getScalarGraphNodeField(getGraphNodeClassName(graph_node));
|
|
271
335
|
}
|
|
272
336
|
|
|
273
337
|
/**
|
|
@@ -275,20 +339,18 @@ function getOutputNodeClass(graph_node) {
|
|
|
275
339
|
* @returns {string}
|
|
276
340
|
*/
|
|
277
341
|
function getOutputNodeId(graph_node) {
|
|
278
|
-
return (
|
|
279
|
-
getScalarGraphNodeField(graph_node.$id ?? graph_node.id) ?? graph_node.id
|
|
280
|
-
);
|
|
342
|
+
return getGraphNodeId(graph_node);
|
|
281
343
|
}
|
|
282
344
|
|
|
283
345
|
/**
|
|
284
346
|
* @param {{ label: string, reference: number, target: { kind?: string, path: string, status?: string, title: string } }} resolved_link
|
|
285
|
-
* @param {{
|
|
347
|
+
* @param {{ document_path_ids?: BuildGraphResult['document_path_ids'], graph_nodes?: BuildGraphResult['nodes'], repo_config?: PatramRepoConfig }} command_options
|
|
286
348
|
* @returns {OutputResolvedLinkItem}
|
|
287
349
|
*/
|
|
288
350
|
function createResolvedLinkOutputItem(resolved_link, command_options) {
|
|
289
351
|
const target_graph_node = resolveDocumentGraphNode(
|
|
290
352
|
command_options.graph_nodes,
|
|
291
|
-
command_options.
|
|
353
|
+
command_options.document_path_ids,
|
|
292
354
|
resolved_link.target.path,
|
|
293
355
|
);
|
|
294
356
|
|
|
@@ -299,11 +361,6 @@ function createResolvedLinkOutputItem(resolved_link, command_options) {
|
|
|
299
361
|
target: createResolvedLinkTarget(
|
|
300
362
|
resolved_link.target,
|
|
301
363
|
command_options.repo_config?.fields ?? {},
|
|
302
|
-
target_graph_node
|
|
303
|
-
? (command_options.derived_summary_evaluator?.evaluate(
|
|
304
|
-
target_graph_node,
|
|
305
|
-
) ?? null)
|
|
306
|
-
: null,
|
|
307
364
|
target_graph_node,
|
|
308
365
|
),
|
|
309
366
|
};
|
|
@@ -311,20 +368,20 @@ function createResolvedLinkOutputItem(resolved_link, command_options) {
|
|
|
311
368
|
|
|
312
369
|
/**
|
|
313
370
|
* @param {BuildGraphResult['nodes'] | undefined} graph_nodes
|
|
314
|
-
* @param {BuildGraphResult['
|
|
371
|
+
* @param {BuildGraphResult['document_path_ids'] | undefined} document_path_ids
|
|
315
372
|
* @param {string} document_path
|
|
316
373
|
* @returns {GraphNode | undefined}
|
|
317
374
|
*/
|
|
318
375
|
function resolveDocumentGraphNode(
|
|
319
376
|
graph_nodes,
|
|
320
|
-
|
|
377
|
+
document_path_ids,
|
|
321
378
|
document_path,
|
|
322
379
|
) {
|
|
323
380
|
if (!graph_nodes) {
|
|
324
381
|
return undefined;
|
|
325
382
|
}
|
|
326
383
|
|
|
327
|
-
return graph_nodes[resolveDocumentNodeId(
|
|
384
|
+
return graph_nodes[resolveDocumentNodeId(document_path_ids, document_path)];
|
|
328
385
|
}
|
|
329
386
|
|
|
330
387
|
/**
|
|
@@ -335,10 +392,10 @@ function resolveDocumentGraphNode(
|
|
|
335
392
|
function collectOutputFields(graph_node, field_definitions) {
|
|
336
393
|
/** @type {Record<string, string | string[]>} */
|
|
337
394
|
const fields = {};
|
|
395
|
+
const metadata_entries = Object.entries(graph_node.metadata ?? {});
|
|
338
396
|
|
|
339
|
-
for (const [field_name, field_value] of
|
|
397
|
+
for (const [field_name, field_value] of metadata_entries) {
|
|
340
398
|
const normalized_value = getCollectedOutputFieldValue(
|
|
341
|
-
graph_node,
|
|
342
399
|
field_name,
|
|
343
400
|
field_value,
|
|
344
401
|
);
|
|
@@ -355,7 +412,9 @@ function collectOutputFields(graph_node, field_definitions) {
|
|
|
355
412
|
continue;
|
|
356
413
|
}
|
|
357
414
|
|
|
358
|
-
const field_value = normalizeOutputFieldValue(
|
|
415
|
+
const field_value = normalizeOutputFieldValue(
|
|
416
|
+
getGraphNodeMetadataValue(graph_node, field_name),
|
|
417
|
+
);
|
|
359
418
|
|
|
360
419
|
if (field_value !== undefined) {
|
|
361
420
|
fields[field_name] = field_value;
|
|
@@ -366,12 +425,11 @@ function collectOutputFields(graph_node, field_definitions) {
|
|
|
366
425
|
}
|
|
367
426
|
|
|
368
427
|
/**
|
|
369
|
-
* @param {GraphNode} graph_node
|
|
370
428
|
* @param {string} field_name
|
|
371
429
|
* @param {unknown} field_value
|
|
372
430
|
* @returns {string | string[] | undefined}
|
|
373
431
|
*/
|
|
374
|
-
function getCollectedOutputFieldValue(
|
|
432
|
+
function getCollectedOutputFieldValue(field_name, field_value) {
|
|
375
433
|
if (isInternalOutputField(field_name)) {
|
|
376
434
|
return undefined;
|
|
377
435
|
}
|
|
@@ -382,39 +440,9 @@ function getCollectedOutputFieldValue(graph_node, field_name, field_value) {
|
|
|
382
440
|
return undefined;
|
|
383
441
|
}
|
|
384
442
|
|
|
385
|
-
if (isLegacyMirrorOutputField(graph_node, field_name, normalized_value)) {
|
|
386
|
-
return undefined;
|
|
387
|
-
}
|
|
388
|
-
|
|
389
443
|
return normalized_value;
|
|
390
444
|
}
|
|
391
445
|
|
|
392
|
-
/**
|
|
393
|
-
* @param {GraphNode} graph_node
|
|
394
|
-
* @param {string} field_name
|
|
395
|
-
* @param {string | string[]} normalized_value
|
|
396
|
-
* @returns {boolean}
|
|
397
|
-
*/
|
|
398
|
-
function isLegacyMirrorOutputField(graph_node, field_name, normalized_value) {
|
|
399
|
-
if (Array.isArray(normalized_value)) {
|
|
400
|
-
return false;
|
|
401
|
-
}
|
|
402
|
-
|
|
403
|
-
if (field_name === 'kind') {
|
|
404
|
-
return normalized_value === graph_node.$class;
|
|
405
|
-
}
|
|
406
|
-
|
|
407
|
-
if (field_name === 'path') {
|
|
408
|
-
return normalized_value === graph_node.$path;
|
|
409
|
-
}
|
|
410
|
-
|
|
411
|
-
if (field_name === 'id') {
|
|
412
|
-
return normalized_value === graph_node.$id;
|
|
413
|
-
}
|
|
414
|
-
|
|
415
|
-
return false;
|
|
416
|
-
}
|
|
417
|
-
|
|
418
446
|
/**
|
|
419
447
|
* @param {Record<string, string | string[]>} fields
|
|
420
448
|
* @param {NonNullable<PatramRepoConfig['fields']>} field_definitions
|
|
@@ -423,7 +451,9 @@ function isLegacyMirrorOutputField(graph_node, field_name, normalized_value) {
|
|
|
423
451
|
function createVisibleOutputFields(fields, field_definitions) {
|
|
424
452
|
return Object.entries(fields)
|
|
425
453
|
.filter(
|
|
426
|
-
([field_name]) =>
|
|
454
|
+
([field_name]) =>
|
|
455
|
+
field_name !== 'description' &&
|
|
456
|
+
field_definitions[field_name]?.hidden !== true,
|
|
427
457
|
)
|
|
428
458
|
.sort(([left_name], [right_name]) =>
|
|
429
459
|
compareOutputFieldNames(left_name, right_name, field_definitions),
|
|
@@ -436,16 +466,7 @@ function createVisibleOutputFields(fields, field_definitions) {
|
|
|
436
466
|
* @returns {boolean}
|
|
437
467
|
*/
|
|
438
468
|
function isInternalOutputField(field_name) {
|
|
439
|
-
return
|
|
440
|
-
field_name === '$class' ||
|
|
441
|
-
field_name === '$id' ||
|
|
442
|
-
field_name === '$path' ||
|
|
443
|
-
field_name === 'id' ||
|
|
444
|
-
field_name === 'key' ||
|
|
445
|
-
field_name === 'label' ||
|
|
446
|
-
field_name === 'path' ||
|
|
447
|
-
field_name === 'title'
|
|
448
|
-
);
|
|
469
|
+
return field_name === 'title';
|
|
449
470
|
}
|
|
450
471
|
|
|
451
472
|
/**
|
|
@@ -456,9 +477,9 @@ function isInternalOutputField(field_name) {
|
|
|
456
477
|
*/
|
|
457
478
|
function compareOutputFieldNames(left_name, right_name, field_definitions) {
|
|
458
479
|
const left_order =
|
|
459
|
-
field_definitions[left_name]?.
|
|
480
|
+
field_definitions[left_name]?.order ?? Number.MAX_SAFE_INTEGER;
|
|
460
481
|
const right_order =
|
|
461
|
-
field_definitions[right_name]?.
|
|
482
|
+
field_definitions[right_name]?.order ?? Number.MAX_SAFE_INTEGER;
|
|
462
483
|
|
|
463
484
|
if (left_order !== right_order) {
|
|
464
485
|
return left_order - right_order;
|
|
@@ -10,7 +10,7 @@ export function collectJsdocBlocks(source_text) {
|
|
|
10
10
|
const jsdoc_blocks = [];
|
|
11
11
|
|
|
12
12
|
for (let line_index = 0; line_index < source_lines.length; line_index += 1) {
|
|
13
|
-
if (
|
|
13
|
+
if (!/^\s*\/\*\*/du.test(source_lines[line_index])) {
|
|
14
14
|
continue;
|
|
15
15
|
}
|
|
16
16
|
|
|
@@ -22,10 +22,10 @@ import { JSDOC_SOURCE_FILE_EXTENSIONS } from '../../config/source-file-defaults.
|
|
|
22
22
|
* Activates one source anchor block, extracts directives and links, and
|
|
23
23
|
* derives title and description claims from prose.
|
|
24
24
|
*
|
|
25
|
-
*
|
|
26
|
-
*
|
|
27
|
-
*
|
|
28
|
-
*
|
|
25
|
+
* kind: parse
|
|
26
|
+
* status: active
|
|
27
|
+
* tracked_in: ../../../docs/plans/v0/source-anchor-dogfooding.md
|
|
28
|
+
* decided_by: ../../../docs/decisions/jsdoc-metadata-directive-syntax.md
|
|
29
29
|
* @patram
|
|
30
30
|
* @see {@link ../parse-claims.js}
|
|
31
31
|
* @see {@link ../../../docs/decisions/jsdoc-metadata-directive-syntax.md}
|
|
@@ -34,7 +34,7 @@ import { JSDOC_SOURCE_FILE_EXTENSIONS } from '../../config/source-file-defaults.
|
|
|
34
34
|
const JSDOC_EXTENSIONS = new Set(JSDOC_SOURCE_FILE_EXTENSIONS);
|
|
35
35
|
const JSDOC_LINK_TAG_PATTERN = /^@(link|see)\s+(.+)$/du;
|
|
36
36
|
const JSDOC_TAG_PATTERN = /^@[A-Za-z]+(?:\s|$)/du;
|
|
37
|
-
const JSDOC_VISIBLE_DIRECTIVE_PATTERN = /^([
|
|
37
|
+
const JSDOC_VISIBLE_DIRECTIVE_PATTERN = /^([a-z][a-z0-9_]*):\s+(.+)$/du;
|
|
38
38
|
|
|
39
39
|
/**
|
|
40
40
|
* Parse JSDoc metadata claims from one source file.
|
|
@@ -160,8 +160,14 @@ function matchJsdocDirectiveFields(file_path, block_line) {
|
|
|
160
160
|
return null;
|
|
161
161
|
}
|
|
162
162
|
|
|
163
|
+
const directive_name = normalizeDirectiveName(directive_match[1]);
|
|
164
|
+
|
|
165
|
+
if (!directive_name) {
|
|
166
|
+
return null;
|
|
167
|
+
}
|
|
168
|
+
|
|
163
169
|
return {
|
|
164
|
-
name:
|
|
170
|
+
name: directive_name,
|
|
165
171
|
origin: {
|
|
166
172
|
column: block_line.column,
|
|
167
173
|
line: block_line.line,
|