@principal-ai/subsystems-react 0.20.5 → 0.21.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/README.md +1 -1
- package/dist/graphify/anchor.d.ts +17 -0
- package/dist/graphify/anchor.d.ts.map +1 -1
- package/dist/graphify/anchor.js +41 -0
- package/dist/graphify/anchor.js.map +1 -1
- package/dist/graphify/consolidated.d.ts +40 -1
- package/dist/graphify/consolidated.d.ts.map +1 -1
- package/dist/graphify/construct.d.ts +23 -0
- package/dist/graphify/construct.d.ts.map +1 -0
- package/dist/graphify/construct.js +77 -0
- package/dist/graphify/construct.js.map +1 -0
- package/dist/graphify/index.d.ts +2 -2
- package/dist/graphify/index.d.ts.map +1 -1
- package/dist/graphify/index.js +1 -1
- package/dist/graphify/index.js.map +1 -1
- package/dist/index.d.ts +7 -7
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +3 -3
- package/dist/index.js.map +1 -1
- package/dist/pierre/PierreWalkthroughCodeView.d.ts +22 -0
- package/dist/pierre/PierreWalkthroughCodeView.d.ts.map +1 -0
- package/dist/pierre/PierreWalkthroughCodeView.js +198 -0
- package/dist/pierre/PierreWalkthroughCodeView.js.map +1 -0
- package/dist/pierre/index.d.ts +2 -2
- package/dist/pierre/index.js +1 -1
- package/dist/pierre/pierreFileLang.d.ts +1 -1
- package/dist/pierre/pierreFileLang.js +1 -1
- package/dist/stories/Subsystem/ComponentGraph/fixtures.d.ts +14 -2
- package/dist/stories/Subsystem/ComponentGraph/fixtures.d.ts.map +1 -1
- package/dist/stories/Subsystem/ComponentGraph/fixtures.js +86 -20
- package/dist/stories/Subsystem/ComponentGraph/fixtures.js.map +1 -1
- package/dist/subsystem/ComponentDeclaration.js +1 -1
- package/dist/subsystem/ComponentDeclaration.js.map +1 -1
- package/dist/subsystem/FileDrawer.d.ts +2 -2
- package/dist/subsystem/FileDrawer.js +2 -2
- package/dist/subsystem/SubsystemComponentGraph.d.ts +25 -24
- package/dist/subsystem/SubsystemComponentGraph.d.ts.map +1 -1
- package/dist/subsystem/SubsystemComponentGraph.js +220 -194
- package/dist/subsystem/SubsystemComponentGraph.js.map +1 -1
- package/dist/subsystem/formatDeclaration.d.ts +2 -1
- package/dist/subsystem/formatDeclaration.d.ts.map +1 -1
- package/dist/subsystem/formatDeclaration.js +57 -33
- package/dist/subsystem/formatDeclaration.js.map +1 -1
- package/dist/subsystem/model.d.ts +109 -42
- package/dist/subsystem/model.d.ts.map +1 -1
- package/dist/subsystem/model.js +107 -5
- package/dist/subsystem/model.js.map +1 -1
- package/dist/subsystem/nodes.d.ts.map +1 -1
- package/dist/subsystem/nodes.js +43 -18
- package/dist/subsystem/nodes.js.map +1 -1
- package/dist/subsystem/tokenizeComponent.js +2 -2
- package/dist/subsystem/tokenizeComponent.js.map +1 -1
- package/package.json +3 -3
- package/src/graphify/anchor.test.ts +31 -2
- package/src/graphify/anchor.ts +46 -0
- package/src/graphify/consolidated.ts +43 -1
- package/src/graphify/{kind.test.ts → construct.test.ts} +20 -20
- package/src/graphify/{kind.ts → construct.ts} +17 -17
- package/src/graphify/index.ts +5 -2
- package/src/index.ts +20 -9
- package/src/pierre/{PierreThroughlineCodeView.tsx → PierreWalkthroughCodeView.tsx} +39 -47
- package/src/pierre/index.ts +2 -2
- package/src/pierre/pierreFileLang.ts +1 -1
- package/src/stories/Pierre/CodeView.stories.tsx +3 -3
- package/src/stories/Subsystem/ComponentDeclarationAudit.stories.tsx +14 -14
- package/src/stories/Subsystem/ComponentGraph/Appearance.stories.tsx +13 -15
- package/src/stories/Subsystem/ComponentGraph/Basics.stories.tsx +8 -8
- package/src/stories/Subsystem/ComponentGraph/Captures.stories.tsx +16 -20
- package/src/stories/Subsystem/ComponentGraph/CustomEntities.stories.tsx +11 -10
- package/src/stories/Subsystem/ComponentGraph/DetailPanel.stories.tsx +13 -14
- package/src/stories/Subsystem/ComponentGraph/Flows.stories.tsx +31 -66
- package/src/stories/Subsystem/ComponentGraph/FrameworkStereotype.stories.tsx +2 -2
- package/src/stories/Subsystem/ComponentGraph/GraphTitle.stories.tsx +4 -4
- package/src/stories/Subsystem/ComponentGraph/Processes.stories.tsx +3 -3
- package/src/stories/Subsystem/ComponentGraph/Proposed.stories.tsx +254 -0
- package/src/stories/Subsystem/ComponentGraph/Scenarios.stories.tsx +518 -33
- package/src/stories/Subsystem/ComponentGraph/Spotlights.stories.tsx +13 -13
- package/src/stories/Subsystem/ComponentGraph/fixtures.ts +105 -21
- package/src/subsystem/ComponentDeclaration.tsx +1 -1
- package/src/subsystem/FileDrawer.tsx +2 -2
- package/src/subsystem/SubsystemComponentGraph.tsx +284 -254
- package/src/subsystem/formatDeclaration.test.ts +76 -1
- package/src/subsystem/formatDeclaration.ts +57 -33
- package/src/subsystem/model.test.ts +49 -15
- package/src/subsystem/model.ts +210 -51
- package/src/subsystem/nodes.tsx +63 -22
- package/src/subsystem/tokenizeComponent.ts +2 -2
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
2
|
+
* PierreWalkthroughCodeView — multi-file step snippets via `@pierre/diffs` CodeView.
|
|
3
3
|
*
|
|
4
|
-
* Renders one sliced window per
|
|
4
|
+
* Renders one sliced window per walkthrough step in a single virtualized
|
|
5
5
|
* scroll; when `stepIndex` changes, scrolls that step's site line into view
|
|
6
6
|
* and highlights it via CodeView `selectedLines` (same mechanism as
|
|
7
7
|
* `PierreSnippetView`).
|
|
@@ -22,10 +22,10 @@ type CodeViewLineSelection = {
|
|
|
22
22
|
id: string;
|
|
23
23
|
range: { start: number; end: number };
|
|
24
24
|
};
|
|
25
|
-
/** Metadata carried on a
|
|
26
|
-
type
|
|
25
|
+
/** Metadata carried on a walkthrough step's line annotation. */
|
|
26
|
+
type WalkthroughStepAnnotation = { text: string };
|
|
27
27
|
import { useTheme } from '@principal-ade/industry-theme';
|
|
28
|
-
import type {
|
|
28
|
+
import type { SubsystemWalkthrough } from '../subsystem/model';
|
|
29
29
|
import { buildPierreOptions, PIERRE_FILE_STYLE } from './pierreBackground';
|
|
30
30
|
import {
|
|
31
31
|
pierreCodeViewFileName,
|
|
@@ -34,8 +34,8 @@ import {
|
|
|
34
34
|
import { resolvePierreSyntaxThemeName } from './pierreSyntaxTheme';
|
|
35
35
|
import { sliceSnippetWindow, type SnippetSlice } from './sliceSnippet';
|
|
36
36
|
|
|
37
|
-
export interface
|
|
38
|
-
|
|
37
|
+
export interface PierreWalkthroughCodeViewProps {
|
|
38
|
+
walkthrough: SubsystemWalkthrough;
|
|
39
39
|
/** Focused step; `null` shows all snippets without scrolling to a step. */
|
|
40
40
|
stepIndex: number | null;
|
|
41
41
|
readFile: (path: string) => Promise<string>;
|
|
@@ -50,31 +50,31 @@ type FileLoadState =
|
|
|
50
50
|
| { status: 'error'; message: string }
|
|
51
51
|
| { status: 'ready'; byPath: Map<string, string> };
|
|
52
52
|
|
|
53
|
-
function stepItemId(
|
|
54
|
-
return `${
|
|
53
|
+
function stepItemId(walkthroughId: string, index: number): string {
|
|
54
|
+
return `${walkthroughId}:${index}`;
|
|
55
55
|
}
|
|
56
56
|
|
|
57
|
-
export function
|
|
58
|
-
|
|
57
|
+
export function PierreWalkthroughCodeView({
|
|
58
|
+
walkthrough,
|
|
59
59
|
stepIndex,
|
|
60
60
|
readFile,
|
|
61
61
|
contextLines = 8,
|
|
62
62
|
background,
|
|
63
|
-
}:
|
|
63
|
+
}: PierreWalkthroughCodeViewProps) {
|
|
64
64
|
const { theme, mode } = useTheme();
|
|
65
65
|
const viewRef = useRef<CodeViewHandle<undefined>>(null);
|
|
66
66
|
const [load, setLoad] = useState<FileLoadState>({ status: 'loading' });
|
|
67
67
|
|
|
68
68
|
const pathsKey = useMemo(() => {
|
|
69
|
-
const paths = [...new Set(
|
|
69
|
+
const paths = [...new Set(walkthrough.steps.map((s) => s.file))];
|
|
70
70
|
paths.sort();
|
|
71
71
|
return paths.join('\0');
|
|
72
|
-
}, [
|
|
72
|
+
}, [walkthrough.steps]);
|
|
73
73
|
|
|
74
74
|
useEffect(() => {
|
|
75
75
|
let cancelled = false;
|
|
76
76
|
setLoad({ status: 'loading' });
|
|
77
|
-
const paths = [...new Set(
|
|
77
|
+
const paths = [...new Set(walkthrough.steps.map((s) => s.file))];
|
|
78
78
|
void Promise.all(
|
|
79
79
|
paths.map(async (path) => {
|
|
80
80
|
const contents = await readFile(path);
|
|
@@ -95,11 +95,11 @@ export function PierreThroughlineCodeView({
|
|
|
95
95
|
return () => {
|
|
96
96
|
cancelled = true;
|
|
97
97
|
};
|
|
98
|
-
}, [
|
|
98
|
+
}, [walkthrough.id, pathsKey, readFile]);
|
|
99
99
|
|
|
100
100
|
const slices = useMemo((): SnippetSlice[] => {
|
|
101
101
|
if (load.status !== 'ready') return [];
|
|
102
|
-
return
|
|
102
|
+
return walkthrough.steps.map((step) => {
|
|
103
103
|
const contents = load.byPath.get(step.file) ?? '';
|
|
104
104
|
return sliceSnippetWindow(
|
|
105
105
|
contents,
|
|
@@ -109,15 +109,15 @@ export function PierreThroughlineCodeView({
|
|
|
109
109
|
step.line,
|
|
110
110
|
);
|
|
111
111
|
});
|
|
112
|
-
}, [load,
|
|
112
|
+
}, [load, walkthrough.steps, contextLines]);
|
|
113
113
|
|
|
114
|
-
const items = useMemo((): CodeViewItem<
|
|
114
|
+
const items = useMemo((): CodeViewItem<WalkthroughStepAnnotation>[] => {
|
|
115
115
|
if (load.status !== 'ready' || slices.length === 0) return [];
|
|
116
|
-
return
|
|
116
|
+
return walkthrough.steps.map((step, index) => {
|
|
117
117
|
const slice = slices[index]!;
|
|
118
118
|
const focus = slice.focusOffset;
|
|
119
119
|
const annotations:
|
|
120
|
-
| LineAnnotation<
|
|
120
|
+
| LineAnnotation<WalkthroughStepAnnotation>[]
|
|
121
121
|
| undefined =
|
|
122
122
|
step.annotation != null && step.annotation.length > 0 && focus != null
|
|
123
123
|
? [
|
|
@@ -128,26 +128,20 @@ const items = useMemo((): CodeViewItem<ThroughlineStepAnnotation>[] => {
|
|
|
128
128
|
]
|
|
129
129
|
: undefined;
|
|
130
130
|
return {
|
|
131
|
-
id: stepItemId(
|
|
131
|
+
id: stepItemId(walkthrough.id, index),
|
|
132
132
|
type: 'file' as const,
|
|
133
133
|
version: 1,
|
|
134
134
|
annotations,
|
|
135
135
|
file: {
|
|
136
|
-
// Unique per-step name: many throughline steps share one path
|
|
137
|
-
// (e.g. seven sites in main.cpp), and identical `name`s have
|
|
138
|
-
// correlated with WebKit renderer traps in CodeView.
|
|
139
136
|
name: pierreCodeViewFileName(step.file, index),
|
|
140
137
|
contents: slice.contents,
|
|
141
|
-
// C-family → plain text: cpp Shiki still traps WebKit even with
|
|
142
|
-
// unique names (reproduced on 0.16.67).
|
|
143
138
|
lang: pierreLangForPath(step.file),
|
|
144
|
-
cacheKey: `${
|
|
139
|
+
cacheKey: `${walkthrough.id}:${index}:${step.file}:${step.line}:${slice.sliceStart}-${slice.sliceEnd}`,
|
|
145
140
|
},
|
|
146
141
|
};
|
|
147
142
|
});
|
|
148
|
-
}, [load, slices,
|
|
143
|
+
}, [load, slices, walkthrough.id, walkthrough.steps]);
|
|
149
144
|
|
|
150
|
-
/** Highlight the focused step's site line (1-based within its sliced window). */
|
|
151
145
|
const selectedLines = useMemo((): CodeViewLineSelection | null => {
|
|
152
146
|
if (stepIndex == null || stepIndex < 0 || stepIndex >= slices.length) {
|
|
153
147
|
return null;
|
|
@@ -155,15 +149,15 @@ const items = useMemo((): CodeViewItem<ThroughlineStepAnnotation>[] => {
|
|
|
155
149
|
const focus = slices[stepIndex]?.focusOffset;
|
|
156
150
|
if (focus == null) return null;
|
|
157
151
|
return {
|
|
158
|
-
id: stepItemId(
|
|
152
|
+
id: stepItemId(walkthrough.id, stepIndex),
|
|
159
153
|
range: { start: focus, end: focus },
|
|
160
154
|
};
|
|
161
|
-
}, [stepIndex, slices,
|
|
155
|
+
}, [stepIndex, slices, walkthrough.id]);
|
|
162
156
|
|
|
163
157
|
const renderHeaderPrefix = useMemo(() => {
|
|
164
158
|
return (item: CodeViewItem) => {
|
|
165
159
|
const index = Number.parseInt(item.id.split(':').pop() ?? '', 10);
|
|
166
|
-
const step =
|
|
160
|
+
const step = walkthrough.steps[index];
|
|
167
161
|
if (!step) return null;
|
|
168
162
|
const label =
|
|
169
163
|
step.symbol != null && step.symbol.length > 0
|
|
@@ -182,12 +176,12 @@ const items = useMemo((): CodeViewItem<ThroughlineStepAnnotation>[] => {
|
|
|
182
176
|
</span>
|
|
183
177
|
);
|
|
184
178
|
};
|
|
185
|
-
}, [
|
|
179
|
+
}, [walkthrough.steps, theme]);
|
|
186
180
|
|
|
187
181
|
const renderHeaderMetadata = useMemo(() => {
|
|
188
182
|
return (item: CodeViewItem) => {
|
|
189
183
|
const index = Number.parseInt(item.id.split(':').pop() ?? '', 10);
|
|
190
|
-
const step =
|
|
184
|
+
const step = walkthrough.steps[index];
|
|
191
185
|
if (!step) return null;
|
|
192
186
|
return (
|
|
193
187
|
<span
|
|
@@ -202,17 +196,17 @@ const items = useMemo((): CodeViewItem<ThroughlineStepAnnotation>[] => {
|
|
|
202
196
|
</span>
|
|
203
197
|
);
|
|
204
198
|
};
|
|
205
|
-
}, [
|
|
199
|
+
}, [walkthrough.steps, theme]);
|
|
206
200
|
|
|
207
201
|
const renderAnnotation = useMemo(() => {
|
|
208
202
|
return (
|
|
209
203
|
annotation:
|
|
210
|
-
| LineAnnotation<
|
|
211
|
-
| DiffLineAnnotation<
|
|
212
|
-
item: CodeViewItem<
|
|
204
|
+
| LineAnnotation<WalkthroughStepAnnotation>
|
|
205
|
+
| DiffLineAnnotation<WalkthroughStepAnnotation>,
|
|
206
|
+
item: CodeViewItem<WalkthroughStepAnnotation>,
|
|
213
207
|
) => {
|
|
214
208
|
const index = Number.parseInt(item.id.split(':').pop() ?? '', 10);
|
|
215
|
-
const step =
|
|
209
|
+
const step = walkthrough.steps[index];
|
|
216
210
|
const text = annotation.metadata?.text;
|
|
217
211
|
if (!text || !step) return null;
|
|
218
212
|
return (
|
|
@@ -230,7 +224,7 @@ const items = useMemo((): CodeViewItem<ThroughlineStepAnnotation>[] => {
|
|
|
230
224
|
</span>
|
|
231
225
|
);
|
|
232
226
|
};
|
|
233
|
-
}, [
|
|
227
|
+
}, [walkthrough.steps, theme]);
|
|
234
228
|
|
|
235
229
|
const options = useMemo((): CodeViewReactOptions => {
|
|
236
230
|
return {
|
|
@@ -248,11 +242,10 @@ const items = useMemo((): CodeViewItem<ThroughlineStepAnnotation>[] => {
|
|
|
248
242
|
|
|
249
243
|
useEffect(() => {
|
|
250
244
|
if (load.status !== 'ready' || stepIndex == null) return;
|
|
251
|
-
if (stepIndex < 0 || stepIndex >=
|
|
245
|
+
if (stepIndex < 0 || stepIndex >= walkthrough.steps.length) return;
|
|
252
246
|
const focus = slices[stepIndex]?.focusOffset;
|
|
253
247
|
if (focus == null) return;
|
|
254
|
-
|
|
255
|
-
const id = stepItemId(throughline.id, stepIndex);
|
|
248
|
+
const id = stepItemId(walkthrough.id, stepIndex);
|
|
256
249
|
const t = window.setTimeout(() => {
|
|
257
250
|
viewRef.current?.scrollTo({
|
|
258
251
|
type: 'line',
|
|
@@ -265,8 +258,8 @@ const items = useMemo((): CodeViewItem<ThroughlineStepAnnotation>[] => {
|
|
|
265
258
|
}, [
|
|
266
259
|
load.status,
|
|
267
260
|
stepIndex,
|
|
268
|
-
|
|
269
|
-
|
|
261
|
+
walkthrough.id,
|
|
262
|
+
walkthrough.steps.length,
|
|
270
263
|
slices,
|
|
271
264
|
items.length,
|
|
272
265
|
]);
|
|
@@ -286,7 +279,6 @@ const items = useMemo((): CodeViewItem<ThroughlineStepAnnotation>[] => {
|
|
|
286
279
|
);
|
|
287
280
|
}
|
|
288
281
|
|
|
289
|
-
// Pierre's CodeView prop / item unions blow past TS's complexity limit.
|
|
290
282
|
const CodeViewLoose = CodeView as unknown as (props: Record<string, unknown>) => ReactElement;
|
|
291
283
|
|
|
292
284
|
return (
|
package/src/pierre/index.ts
CHANGED
|
@@ -2,8 +2,8 @@ export { PierreFileView } from './PierreFileView';
|
|
|
2
2
|
export type { PierreFileViewProps } from './PierreFileView';
|
|
3
3
|
export { PierreSnippetView } from './PierreSnippetView';
|
|
4
4
|
export type { PierreSnippetViewProps } from './PierreSnippetView';
|
|
5
|
-
export {
|
|
6
|
-
export type {
|
|
5
|
+
export { PierreWalkthroughCodeView } from './PierreWalkthroughCodeView';
|
|
6
|
+
export type { PierreWalkthroughCodeViewProps } from './PierreWalkthroughCodeView';
|
|
7
7
|
export { sliceSnippetWindow } from './sliceSnippet';
|
|
8
8
|
export type { SnippetSlice } from './sliceSnippet';
|
|
9
9
|
export {
|
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
* `file.name`s — so we force plain text for those paths until Pierre/WebKit
|
|
8
8
|
* is safe with them.
|
|
9
9
|
*
|
|
10
|
-
* Distinct
|
|
10
|
+
* Distinct walkthrough slices of the same path still need unique `file.name`s
|
|
11
11
|
* (see `pierreCodeViewFileName`).
|
|
12
12
|
*/
|
|
13
13
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Demo: Pierre CodeView with snippets from different files.
|
|
3
3
|
*
|
|
4
|
-
*
|
|
4
|
+
* Walkthroughs want many short windows across files in one scroll —
|
|
5
5
|
* CodeView is the Pierre primitive for that (virtualized list of file items).
|
|
6
6
|
*/
|
|
7
7
|
import React, { useMemo, useRef } from 'react';
|
|
@@ -54,7 +54,7 @@ const SNIPPETS: SnippetSpec[] = [
|
|
|
54
54
|
startLine: 216,
|
|
55
55
|
endLine: 250,
|
|
56
56
|
focusLine: 216,
|
|
57
|
-
label: '3 ·
|
|
57
|
+
label: '3 · Walkthrough types',
|
|
58
58
|
},
|
|
59
59
|
];
|
|
60
60
|
|
|
@@ -159,7 +159,7 @@ function MultiFileSnippetsDemo() {
|
|
|
159
159
|
}}
|
|
160
160
|
>
|
|
161
161
|
<div style={{ fontSize: 13, fontWeight: 600, marginBottom: 4 }}>
|
|
162
|
-
|
|
162
|
+
Walkthrough steps
|
|
163
163
|
</div>
|
|
164
164
|
<div style={{ fontSize: 12, color: theme.colors.textSecondary, marginBottom: 8 }}>
|
|
165
165
|
Click a step to scroll + highlight its site line.
|
|
@@ -43,7 +43,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
43
43
|
file: 'src/event-processing/sink.ts',
|
|
44
44
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
45
45
|
symbol: 'flush',
|
|
46
|
-
|
|
46
|
+
declaration: {
|
|
47
47
|
kind: 'function',
|
|
48
48
|
parameters: [],
|
|
49
49
|
} satisfies GraphifyComponentDetail,
|
|
@@ -58,7 +58,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
58
58
|
file: 'src/session/SessionReader.ts',
|
|
59
59
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
60
60
|
symbol: 'SessionReader.normalize',
|
|
61
|
-
|
|
61
|
+
declaration: {
|
|
62
62
|
kind: 'function',
|
|
63
63
|
parameters: [{ name: 'session', type: 'SessionRecord' }],
|
|
64
64
|
returnType: 'SessionEvent[]',
|
|
@@ -74,7 +74,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
74
74
|
file: 'src/event-processing/normalize.ts',
|
|
75
75
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
76
76
|
symbol: 'normalizeSession',
|
|
77
|
-
|
|
77
|
+
declaration: {
|
|
78
78
|
kind: 'function',
|
|
79
79
|
parameters: [
|
|
80
80
|
{ name: 'session', type: 'SessionRecord' },
|
|
@@ -93,7 +93,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
93
93
|
file: 'src/session/merge.ts',
|
|
94
94
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
95
95
|
symbol: 'mergeSessions',
|
|
96
|
-
|
|
96
|
+
declaration: {
|
|
97
97
|
kind: 'function',
|
|
98
98
|
parameters: [
|
|
99
99
|
{ name: 'sessions', type: 'SessionRecord[]' },
|
|
@@ -114,7 +114,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
114
114
|
file: 'src/empty.ts',
|
|
115
115
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
116
116
|
symbol: 'EmptyClass',
|
|
117
|
-
|
|
117
|
+
declaration: {
|
|
118
118
|
kind: 'class',
|
|
119
119
|
} satisfies GraphifyComponentDetail,
|
|
120
120
|
},
|
|
@@ -128,7 +128,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
128
128
|
file: 'src/config.ts',
|
|
129
129
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
130
130
|
symbol: 'Config',
|
|
131
|
-
|
|
131
|
+
declaration: {
|
|
132
132
|
kind: 'class',
|
|
133
133
|
properties: [
|
|
134
134
|
{ name: 'host', type: 'string' },
|
|
@@ -147,7 +147,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
147
147
|
file: 'src/event-processing/EventProcessor.ts',
|
|
148
148
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
149
149
|
symbol: 'EventProcessor',
|
|
150
|
-
|
|
150
|
+
declaration: {
|
|
151
151
|
kind: 'class',
|
|
152
152
|
methods: [
|
|
153
153
|
{ name: 'process', parameters: [{ type: 'RawEvent' }, { type: 'ProcessingOptions' }], returnType: 'ProcessedEvent' },
|
|
@@ -174,7 +174,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
174
174
|
file: 'src/session/transcript.ts',
|
|
175
175
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
176
176
|
symbol: 'SessionRecord',
|
|
177
|
-
|
|
177
|
+
declaration: {
|
|
178
178
|
kind: 'type',
|
|
179
179
|
properties: [
|
|
180
180
|
{ name: 'id', type: 'string' },
|
|
@@ -192,7 +192,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
192
192
|
file: 'src/types.ts',
|
|
193
193
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
194
194
|
symbol: 'BrandedId',
|
|
195
|
-
|
|
195
|
+
declaration: {
|
|
196
196
|
kind: 'type',
|
|
197
197
|
} satisfies GraphifyComponentDetail,
|
|
198
198
|
},
|
|
@@ -206,7 +206,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
206
206
|
file: 'src/index.ts',
|
|
207
207
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
208
208
|
symbol: 'index',
|
|
209
|
-
|
|
209
|
+
declaration: {
|
|
210
210
|
kind: 'module',
|
|
211
211
|
imports: [
|
|
212
212
|
{ name: './session/SessionReader' },
|
|
@@ -237,7 +237,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
237
237
|
file: '',
|
|
238
238
|
purl: 'pkg:npm/@principal-ai/subsystems-studio',
|
|
239
239
|
symbol: '',
|
|
240
|
-
|
|
240
|
+
declaration: {
|
|
241
241
|
kind: 'external',
|
|
242
242
|
label: 'pkg:npm/@principal-ai/subsystems-studio',
|
|
243
243
|
} satisfies GraphifyComponentDetail,
|
|
@@ -251,7 +251,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
251
251
|
construct: 'function',
|
|
252
252
|
file: 'src/helpers.ts',
|
|
253
253
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
254
|
-
|
|
254
|
+
declaration: {
|
|
255
255
|
kind: 'function',
|
|
256
256
|
parameters: [{ name: 'input', type: 'string' }],
|
|
257
257
|
returnType: 'void',
|
|
@@ -267,7 +267,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
267
267
|
file: 'src/session/SessionReader.ts',
|
|
268
268
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
269
269
|
symbol: 'SessionReader.normalize',
|
|
270
|
-
|
|
270
|
+
declaration: {
|
|
271
271
|
kind: 'method',
|
|
272
272
|
hostClass: 'SessionReader',
|
|
273
273
|
parameters: [{ name: 'session', type: 'SessionRecord' }],
|
|
@@ -284,7 +284,7 @@ const cases: { label: string; component: SubsystemComponent }[] = [
|
|
|
284
284
|
file: 'src/event-processing/EventProcessor.ts',
|
|
285
285
|
purl: 'pkg:github/principal-ai/agent-monitoring',
|
|
286
286
|
symbol: 'EventProcessor.dispose',
|
|
287
|
-
|
|
287
|
+
declaration: {
|
|
288
288
|
kind: 'method',
|
|
289
289
|
hostClass: 'EventProcessor',
|
|
290
290
|
} satisfies GraphifyComponentDetail,
|
|
@@ -5,7 +5,7 @@ import { ThemeProvider, defaultEditorTheme } from '@principal-ade/industry-theme
|
|
|
5
5
|
import { SubsystemComponentGraph } from '../../../subsystem/SubsystemComponentGraph';
|
|
6
6
|
import type { SubsystemComponent, SubsystemComponentEdge } from '../../../subsystem/model';
|
|
7
7
|
import type { GraphifyComponentDetail } from '../../../graphify';
|
|
8
|
-
import { investigateOnlyComponents,
|
|
8
|
+
import { investigateOnlyComponents, investigateOnlyRelations, investigateOnlyWalkthroughs } from './fixtures';
|
|
9
9
|
|
|
10
10
|
const meta = {
|
|
11
11
|
title: 'Subsystem/ComponentGraph/Appearance',
|
|
@@ -32,7 +32,7 @@ export const NarrowMaxWidth: Story = {
|
|
|
32
32
|
<div style={{ width: '100%', height: '100vh', display: 'flex', flexDirection: 'column' }}>
|
|
33
33
|
<SubsystemComponentGraph
|
|
34
34
|
components={investigateOnlyComponents}
|
|
35
|
-
|
|
35
|
+
relations={investigateOnlyRelations} walkthroughs={investigateOnlyWalkthroughs}
|
|
36
36
|
maxNodeWidth={140}
|
|
37
37
|
/>
|
|
38
38
|
</div>
|
|
@@ -93,7 +93,6 @@ const namingConventionComponents: SubsystemComponent[] = [
|
|
|
93
93
|
},
|
|
94
94
|
];
|
|
95
95
|
|
|
96
|
-
const namingConventionEdges: SubsystemComponentEdge[] = [];
|
|
97
96
|
|
|
98
97
|
/** Nodes with compact `maxNodeWidth` so the different conventions visibly wrap
|
|
99
98
|
* at their word boundaries (camelCase, snake_case, PascalCase, acronyms). */
|
|
@@ -102,7 +101,7 @@ export const NamingConventions: Story = {
|
|
|
102
101
|
<div style={{ width: '100%', height: '100vh', display: 'flex', flexDirection: 'column' }}>
|
|
103
102
|
<SubsystemComponentGraph
|
|
104
103
|
components={namingConventionComponents}
|
|
105
|
-
|
|
104
|
+
relations={[]}
|
|
106
105
|
maxNodeWidth={180}
|
|
107
106
|
/>
|
|
108
107
|
</div>
|
|
@@ -137,7 +136,7 @@ const kindVariationComponents: SubsystemComponent[] = [
|
|
|
137
136
|
purpose: 'members only — methods with typed params + returns, a typed field',
|
|
138
137
|
symbol: 'Transcoder',
|
|
139
138
|
layer: 1,
|
|
140
|
-
|
|
139
|
+
declaration: {
|
|
141
140
|
kind: 'class',
|
|
142
141
|
methods: [
|
|
143
142
|
{ nodeId: 'tm1', name: 'encode', parameters: [{ type: 'RawFrame' }], returnType: 'Uint8Array' },
|
|
@@ -160,7 +159,7 @@ const kindVariationComponents: SubsystemComponent[] = [
|
|
|
160
159
|
purpose: 'relationships only — extends + implements, constructed-by comment; empty body elides the braces',
|
|
161
160
|
symbol: 'HttpTransport',
|
|
162
161
|
layer: 1,
|
|
163
|
-
|
|
162
|
+
declaration: {
|
|
164
163
|
kind: 'class',
|
|
165
164
|
methods: [],
|
|
166
165
|
properties: [],
|
|
@@ -191,7 +190,7 @@ const kindVariationComponents: SubsystemComponent[] = [
|
|
|
191
190
|
purpose: 'signature only — named + positional (type-only) params, array return; no callers/callees comments',
|
|
192
191
|
symbol: 'normalizeSession',
|
|
193
192
|
layer: 2,
|
|
194
|
-
|
|
193
|
+
declaration: {
|
|
195
194
|
kind: 'function',
|
|
196
195
|
parameters: [
|
|
197
196
|
{ name: 'session', type: 'SessionRecord' },
|
|
@@ -211,7 +210,7 @@ const kindVariationComponents: SubsystemComponent[] = [
|
|
|
211
210
|
purpose: 'signature + call relationships — union-typed param, generic return, called-by / calls trailing comments',
|
|
212
211
|
symbol: 'mergeSessions',
|
|
213
212
|
layer: 2,
|
|
214
|
-
|
|
213
|
+
declaration: {
|
|
215
214
|
kind: 'function',
|
|
216
215
|
parameters: [
|
|
217
216
|
{ name: 'sessions', type: 'SessionRecord[]' },
|
|
@@ -243,7 +242,7 @@ const kindVariationComponents: SubsystemComponent[] = [
|
|
|
243
242
|
purpose: 'fields only — typed interface body, nothing else',
|
|
244
243
|
symbol: 'SessionRecord',
|
|
245
244
|
layer: 3,
|
|
246
|
-
|
|
245
|
+
declaration: {
|
|
247
246
|
kind: 'type',
|
|
248
247
|
properties: [
|
|
249
248
|
{ name: 'id', type: 'string' },
|
|
@@ -262,7 +261,7 @@ const kindVariationComponents: SubsystemComponent[] = [
|
|
|
262
261
|
purpose: 'full — fields + implemented-by (clicks through to HttpTransport) + used-by comments',
|
|
263
262
|
symbol: 'Transport',
|
|
264
263
|
layer: 3,
|
|
265
|
-
|
|
264
|
+
declaration: {
|
|
266
265
|
kind: 'type',
|
|
267
266
|
properties: [{ name: 'name', type: 'string' }],
|
|
268
267
|
usedBy: [{ nodeId: 'u1', name: 'main', context: 'parameter_type' }],
|
|
@@ -290,7 +289,7 @@ const kindVariationComponents: SubsystemComponent[] = [
|
|
|
290
289
|
purpose: 'exports only — export statement + defines comment',
|
|
291
290
|
symbol: '',
|
|
292
291
|
layer: 4,
|
|
293
|
-
|
|
292
|
+
declaration: {
|
|
294
293
|
kind: 'module',
|
|
295
294
|
exports: ['extractToolName', 'extractFilePath'],
|
|
296
295
|
imports: [],
|
|
@@ -306,7 +305,7 @@ const kindVariationComponents: SubsystemComponent[] = [
|
|
|
306
305
|
purpose: 'full — import statements + re-export statement + defines comment',
|
|
307
306
|
symbol: '',
|
|
308
307
|
layer: 4,
|
|
309
|
-
|
|
308
|
+
declaration: {
|
|
310
309
|
kind: 'module',
|
|
311
310
|
exports: ['SessionReader', 'SessionStore'],
|
|
312
311
|
imports: [{ nodeId: 'i1', name: 'transcript', relation: 'imports_from' }],
|
|
@@ -334,14 +333,13 @@ const kindVariationComponents: SubsystemComponent[] = [
|
|
|
334
333
|
purpose: 'labeled — the full purl as a quoted string literal',
|
|
335
334
|
symbol: '',
|
|
336
335
|
layer: 5,
|
|
337
|
-
|
|
336
|
+
declaration: {
|
|
338
337
|
kind: 'external',
|
|
339
338
|
label: 'pkg:npm/@principal-ai/subsystems-studio',
|
|
340
339
|
} satisfies GraphifyComponentDetail,
|
|
341
340
|
},
|
|
342
341
|
];
|
|
343
342
|
|
|
344
|
-
const kindVariationEdges: SubsystemComponentEdge[] = [];
|
|
345
343
|
|
|
346
344
|
function KindVariationsDemo() {
|
|
347
345
|
const [selected, setSelected] = useState<string | null>(null);
|
|
@@ -349,7 +347,7 @@ function KindVariationsDemo() {
|
|
|
349
347
|
<div style={{ width: '100%', height: '100vh', display: 'flex', flexDirection: 'column' }}>
|
|
350
348
|
<SubsystemComponentGraph
|
|
351
349
|
components={kindVariationComponents}
|
|
352
|
-
|
|
350
|
+
relations={[]}
|
|
353
351
|
onSelect={(id) => setSelected(id)}
|
|
354
352
|
/>
|
|
355
353
|
<div style={{ marginTop: 8, fontFamily: 'monospace', fontSize: 12, color: '#aaa' }}>
|
|
@@ -4,7 +4,7 @@ import type { Meta, StoryObj } from '@storybook/react';
|
|
|
4
4
|
import { ThemeProvider, defaultEditorTheme } from '@principal-ade/industry-theme';
|
|
5
5
|
import { SubsystemComponentGraph } from '../../../subsystem/SubsystemComponentGraph';
|
|
6
6
|
import type { SubsystemComponent, SubsystemComponentEdge } from '../../../subsystem/model';
|
|
7
|
-
import { components,
|
|
7
|
+
import { components, graphSpecFromEdges } from './fixtures';
|
|
8
8
|
|
|
9
9
|
const meta = {
|
|
10
10
|
title: 'Subsystem/ComponentGraph/Basics',
|
|
@@ -33,7 +33,7 @@ const twoNodeComponents = components([
|
|
|
33
33
|
['dst', 'SessionReader', 'class', 'SessionReader.ts', 'pkg:github/principal-ai/agent-monitoring', 'normalizes sessions into events'],
|
|
34
34
|
]);
|
|
35
35
|
|
|
36
|
-
const twoNodeEdges =
|
|
36
|
+
const twoNodeEdges = graphSpecFromEdges([
|
|
37
37
|
['src', 'dst', 'imports'],
|
|
38
38
|
]);
|
|
39
39
|
|
|
@@ -44,7 +44,7 @@ function TwoNodeDemo({ showEdgeLabels = true }: { showEdgeLabels?: boolean }) {
|
|
|
44
44
|
<div style={{ width: '100%', height: '100vh', display: 'flex', flexDirection: 'column' }}>
|
|
45
45
|
<SubsystemComponentGraph
|
|
46
46
|
components={twoNodeComponents}
|
|
47
|
-
|
|
47
|
+
relations={twoNodeEdges.relations} walkthroughs={twoNodeEdges.walkthroughs}
|
|
48
48
|
onSelect={(id) => setSelected(id)}
|
|
49
49
|
onEdgeSelect={(e) => setSelectedEdge(e)}
|
|
50
50
|
showEdgeLabels={showEdgeLabels}
|
|
@@ -74,7 +74,7 @@ export const TwoNodeNoLabels: Story = {
|
|
|
74
74
|
// ---------------------------------------------------------------------------
|
|
75
75
|
function PlaygroundDemo({ leftCount, rightCount, showEdgeLabels }: { leftCount: number; rightCount: number; showEdgeLabels: boolean }) {
|
|
76
76
|
const comps: SubsystemComponent[] = [];
|
|
77
|
-
const
|
|
77
|
+
const edgeSpec: Array<[string, string, SubsystemComponentEdge['mechanism']]> = [];
|
|
78
78
|
|
|
79
79
|
for (let i = 0; i < leftCount; i++) {
|
|
80
80
|
comps.push({
|
|
@@ -97,16 +97,16 @@ function PlaygroundDemo({ leftCount, rightCount, showEdgeLabels }: { leftCount:
|
|
|
97
97
|
});
|
|
98
98
|
}
|
|
99
99
|
|
|
100
|
-
let ei = 0;
|
|
101
100
|
for (let i = 0; i < leftCount; i++) {
|
|
102
101
|
for (let j = 0; j < rightCount; j++) {
|
|
103
|
-
|
|
102
|
+
edgeSpec.push([`l${i}`, `r${j}`, 'imports']);
|
|
104
103
|
}
|
|
105
104
|
}
|
|
105
|
+
const graph = graphSpecFromEdges(edgeSpec);
|
|
106
106
|
|
|
107
107
|
return (
|
|
108
108
|
<div style={{ width: '100%', height: '100vh', display: 'flex', flexDirection: 'column' }}>
|
|
109
|
-
<SubsystemComponentGraph components={comps}
|
|
109
|
+
<SubsystemComponentGraph components={comps} relations={graph.relations} walkthroughs={graph.walkthroughs} showEdgeLabels={showEdgeLabels} />
|
|
110
110
|
</div>
|
|
111
111
|
);
|
|
112
112
|
}
|
|
@@ -131,7 +131,7 @@ export const Playground: Story = {
|
|
|
131
131
|
export const Empty: Story = {
|
|
132
132
|
render: () => (
|
|
133
133
|
<div style={{ width: '100%', height: '100vh', display: 'flex', flexDirection: 'column' }}>
|
|
134
|
-
<SubsystemComponentGraph components={[]}
|
|
134
|
+
<SubsystemComponentGraph components={[]} relations={[]} />
|
|
135
135
|
</div>
|
|
136
136
|
),
|
|
137
137
|
};
|