@principal-ai/principal-view-cli 0.1.13

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.
@@ -0,0 +1,333 @@
1
+ /**
2
+ * Schema command - Display documentation about the canvas format
3
+ */
4
+ import { Command } from 'commander';
5
+ import chalk from 'chalk';
6
+ const SCHEMA_SECTIONS = {
7
+ overview: `
8
+ ${chalk.bold.cyan('Principal View Canvas Schema')}
9
+ ${chalk.dim('═'.repeat(50))}
10
+
11
+ Canvas files (.canvas) follow the JSON Canvas spec with Principal View extensions.
12
+ All PV extensions are placed in a ${chalk.yellow('"pv"')} field to maintain compatibility
13
+ with standard canvas tools like Obsidian.
14
+
15
+ ${chalk.bold('Required Structure:')}
16
+ ${chalk.dim('┌─────────────────────────────────────────────────┐')}
17
+ ${chalk.dim('│')} { ${chalk.dim('│')}
18
+ ${chalk.dim('│')} ${chalk.green('"nodes"')}: [...], ${chalk.dim('// Required: array of nodes')} ${chalk.dim('│')}
19
+ ${chalk.dim('│')} ${chalk.green('"edges"')}: [...], ${chalk.dim('// Optional: array of edges')} ${chalk.dim('│')}
20
+ ${chalk.dim('│')} ${chalk.green('"pv"')}: { ${chalk.dim('// Required: PV extension')} ${chalk.dim('│')}
21
+ ${chalk.dim('│')} ${chalk.yellow('"name"')}: "...", ${chalk.dim('// Required: graph name')} ${chalk.dim('│')}
22
+ ${chalk.dim('│')} ${chalk.yellow('"version"')}: "..." ${chalk.dim('// Required: schema version')} ${chalk.dim('│')}
23
+ ${chalk.dim('│')} } ${chalk.dim('│')}
24
+ ${chalk.dim('│')} } ${chalk.dim('│')}
25
+ ${chalk.dim('└─────────────────────────────────────────────────┘')}
26
+
27
+ Run ${chalk.cyan('privu schema <section>')} for details on:
28
+ ${chalk.yellow('nodes')} Node types and properties
29
+ ${chalk.yellow('edges')} Edge properties and types
30
+ ${chalk.yellow('vv')} Principal View extension fields
31
+ ${chalk.yellow('examples')} Complete example configurations
32
+ `,
33
+ nodes: `
34
+ ${chalk.bold.cyan('Node Schema')}
35
+ ${chalk.dim('═'.repeat(50))}
36
+
37
+ ${chalk.bold('Required Fields (all nodes):')}
38
+ ${chalk.green('id')} ${chalk.dim('string')} Unique identifier
39
+ ${chalk.green('type')} ${chalk.dim('string')} Node type (see below)
40
+ ${chalk.green('x')} ${chalk.dim('number')} X position in pixels
41
+ ${chalk.green('y')} ${chalk.dim('number')} Y position in pixels
42
+ ${chalk.green('width')} ${chalk.dim('number')} Width in pixels
43
+ ${chalk.green('height')} ${chalk.dim('number')} Height in pixels
44
+
45
+ ${chalk.bold('Optional Fields:')}
46
+ ${chalk.green('color')} ${chalk.dim('string|number')} Hex color or preset (1-6)
47
+
48
+ ${chalk.bold('Standard Node Types:')}
49
+ ${chalk.yellow('text')} Text/markdown content node
50
+ Requires: ${chalk.dim('text')} (string)
51
+
52
+ ${chalk.yellow('group')} Visual container for other nodes
53
+ Optional: ${chalk.dim('label')}, ${chalk.dim('background')}, ${chalk.dim('backgroundStyle')}
54
+
55
+ ${chalk.yellow('file')} Reference to external file
56
+ Requires: ${chalk.dim('file')} (path string)
57
+ Optional: ${chalk.dim('subpath')}
58
+
59
+ ${chalk.yellow('link')} URL reference
60
+ Requires: ${chalk.dim('url')} (string)
61
+
62
+ ${chalk.bold('Custom Node Types:')}
63
+ Any type not in the standard list requires a ${chalk.yellow('vv')} extension:
64
+
65
+ ${chalk.dim('{')}
66
+ ${chalk.green('"id"')}: "my-node",
67
+ ${chalk.green('"type"')}: "api-gateway", ${chalk.dim('// Custom type')}
68
+ ${chalk.green('"x"')}: 100, ${chalk.green('"y"')}: 100,
69
+ ${chalk.green('"width"')}: 150, ${chalk.green('"height"')}: 80,
70
+ ${chalk.green('"pv"')}: {
71
+ ${chalk.yellow('"nodeType"')}: "api-gateway", ${chalk.dim('// Required')}
72
+ ${chalk.yellow('"shape"')}: "rectangle", ${chalk.dim('// Required')}
73
+ ${chalk.cyan('"fill"')}: "#3b82f6", ${chalk.dim('// Optional: fill color')}
74
+ ${chalk.cyan('"stroke"')}: "#1d4ed8", ${chalk.dim('// Optional: border color')}
75
+ ${chalk.cyan('"icon"')}: "Server", ${chalk.dim('// Optional: Lucide icon')}
76
+ ${chalk.cyan('"sources"')}: ["src/api/**"] ${chalk.dim('// Optional: file patterns')}
77
+ }
78
+ ${chalk.dim('}')}
79
+
80
+ ${chalk.bold('Valid Shapes:')}
81
+ ${chalk.cyan('circle')} Circular node
82
+ ${chalk.cyan('rectangle')} Rectangular node (default)
83
+ ${chalk.cyan('hexagon')} Hexagonal node
84
+ ${chalk.cyan('diamond')} Diamond/rhombus node
85
+ ${chalk.cyan('custom')} Custom SVG shape
86
+
87
+ ${chalk.bold('Color Presets:')}
88
+ ${chalk.red('1')} = red ${chalk.hex('#f97316')('2')} = orange ${chalk.yellow('3')} = yellow
89
+ ${chalk.green('4')} = green ${chalk.cyan('5')} = cyan ${chalk.hex('#8b5cf6')('6')} = purple
90
+ `,
91
+ edges: `
92
+ ${chalk.bold.cyan('Edge Schema')}
93
+ ${chalk.dim('═'.repeat(50))}
94
+
95
+ ${chalk.bold('Required Fields:')}
96
+ ${chalk.green('id')} ${chalk.dim('string')} Unique identifier
97
+ ${chalk.green('fromNode')} ${chalk.dim('string')} Source node ID
98
+ ${chalk.green('toNode')} ${chalk.dim('string')} Target node ID
99
+
100
+ ${chalk.bold('Optional Fields:')}
101
+ ${chalk.green('fromSide')} ${chalk.dim('string')} Side of source: top, right, bottom, left
102
+ ${chalk.green('toSide')} ${chalk.dim('string')} Side of target: top, right, bottom, left
103
+ ${chalk.green('fromEnd')} ${chalk.dim('string')} Source endpoint: none, arrow
104
+ ${chalk.green('toEnd')} ${chalk.dim('string')} Target endpoint: none, arrow (default)
105
+ ${chalk.green('color')} ${chalk.dim('string')} Edge color (hex or preset)
106
+ ${chalk.green('label')} ${chalk.dim('string')} Edge label text
107
+
108
+ ${chalk.bold('PV Edge Extension:')}
109
+ ${chalk.dim('{')}
110
+ ${chalk.green('"id"')}: "edge-1",
111
+ ${chalk.green('"fromNode"')}: "api", ${chalk.green('"toNode"')}: "db",
112
+ ${chalk.green('"pv"')}: {
113
+ ${chalk.yellow('"edgeType"')}: "query" ${chalk.dim('// Must be defined in vv.edgeTypes')}
114
+ }
115
+ ${chalk.dim('}')}
116
+
117
+ ${chalk.bold('Defining Edge Types (in canvas vv):')}
118
+ ${chalk.dim('{')}
119
+ ${chalk.green('"pv"')}: {
120
+ "name": "My Graph",
121
+ "version": "1.0.0",
122
+ ${chalk.yellow('"edgeTypes"')}: {
123
+ "query": {
124
+ ${chalk.cyan('"style"')}: "solid", ${chalk.dim('// solid, dashed, dotted, animated')}
125
+ ${chalk.cyan('"color"')}: "#64748b", ${chalk.dim('// Hex color')}
126
+ ${chalk.cyan('"width"')}: 2, ${chalk.dim('// Line width in pixels')}
127
+ ${chalk.cyan('"directed"')}: true, ${chalk.dim('// Show arrow')}
128
+ ${chalk.cyan('"animation"')}: { ${chalk.dim('// Optional animation')}
129
+ "type": "flow", ${chalk.dim('// flow, pulse, particle, glow')}
130
+ "duration": 1000 ${chalk.dim('// Duration in ms')}
131
+ }
132
+ },
133
+ "event": {
134
+ "style": "dashed",
135
+ "color": "#f59e0b"
136
+ }
137
+ }
138
+ }
139
+ ${chalk.dim('}')}
140
+
141
+ ${chalk.bold('Edge Styles:')}
142
+ ${chalk.cyan('solid')} Solid line
143
+ ${chalk.cyan('dashed')} Dashed line
144
+ ${chalk.cyan('dotted')} Dotted line
145
+ ${chalk.cyan('animated')} Animated flowing line
146
+
147
+ ${chalk.bold('Animation Types:')}
148
+ ${chalk.cyan('flow')} Flowing dots along the edge
149
+ ${chalk.cyan('pulse')} Pulsing glow effect
150
+ ${chalk.cyan('particle')} Particle stream
151
+ ${chalk.cyan('glow')} Static glow effect
152
+ `,
153
+ vv: `
154
+ ${chalk.bold.cyan('Principal View Extension')}
155
+ ${chalk.dim('═'.repeat(50))}
156
+
157
+ The ${chalk.yellow('vv')} extension adds rich visualization capabilities while
158
+ maintaining compatibility with standard JSON Canvas tools.
159
+
160
+ ${chalk.bold('Canvas-Level pv (Required):')}
161
+ ${chalk.dim('{')}
162
+ ${chalk.green('"pv"')}: {
163
+ ${chalk.yellow('"name"')}: "My Architecture", ${chalk.dim('// Required: Display name')}
164
+ ${chalk.yellow('"version"')}: "1.0.0", ${chalk.dim('// Required: Schema version')}
165
+ ${chalk.cyan('"description"')}: "...", ${chalk.dim('// Optional: Description')}
166
+ ${chalk.cyan('"edgeTypes"')}: {...}, ${chalk.dim('// Optional: Edge type defs')}
167
+ ${chalk.cyan('"pathConfig"')}: {...}, ${chalk.dim('// Optional: Path matching')}
168
+ ${chalk.cyan('"display"')}: {...} ${chalk.dim('// Optional: Display settings')}
169
+ }
170
+ ${chalk.dim('}')}
171
+
172
+ ${chalk.bold('Node-Level pv (for custom types):')}
173
+ ${chalk.dim('{')}
174
+ ${chalk.green('"pv"')}: {
175
+ ${chalk.yellow('"nodeType"')}: "service", ${chalk.dim('// Required: Type identifier')}
176
+ ${chalk.yellow('"shape"')}: "rectangle", ${chalk.dim('// Required: Visual shape')}
177
+ ${chalk.cyan('"fill"')}: "#3b82f6", ${chalk.dim('// Optional: Fill color (hex)')}
178
+ ${chalk.cyan('"stroke"')}: "#1d4ed8", ${chalk.dim('// Optional: Border color (hex)')}
179
+ ${chalk.cyan('"icon"')}: "Server", ${chalk.dim('// Optional: Lucide icon name')}
180
+ ${chalk.cyan('"sources"')}: ["src/**/*.ts"], ${chalk.dim('// Optional: Source patterns')}
181
+ ${chalk.cyan('"states"')}: { ${chalk.dim('// Optional: State definitions')}
182
+ "active": { "color": "#22c55e" },
183
+ "error": { "color": "#ef4444" }
184
+ },
185
+ ${chalk.cyan('"actions"')}: [{ ${chalk.dim('// Optional: Action patterns')}
186
+ "pattern": "request.*",
187
+ "event": "request",
188
+ "state": "active"
189
+ }]
190
+ }
191
+ ${chalk.dim('}')}
192
+
193
+ ${chalk.bold('Edge-Level vv:')}
194
+ ${chalk.dim('{')}
195
+ ${chalk.green('"pv"')}: {
196
+ ${chalk.yellow('"edgeType"')}: "query", ${chalk.dim('// References vv.edgeTypes')}
197
+ ${chalk.cyan('"style"')}: "solid", ${chalk.dim('// Override: line style')}
198
+ ${chalk.cyan('"width"')}: 2, ${chalk.dim('// Override: line width')}
199
+ ${chalk.cyan('"animation"')}: {...} ${chalk.dim('// Override: animation')}
200
+ }
201
+ ${chalk.dim('}')}
202
+
203
+ ${chalk.bold('Path Configuration (vv.pathConfig):')}
204
+ ${chalk.cyan('"pathConfig"')}: {
205
+ "projectRoot": "./", ${chalk.dim('// Project root path')}
206
+ "captureSource": true, ${chalk.dim('// Capture source locations')}
207
+ "enableActionPatterns": true, ${chalk.dim('// Enable action matching')}
208
+ "logLevel": "info", ${chalk.dim('// Minimum log level')}
209
+ "ignoreUnsourced": false ${chalk.dim('// Ignore logs without source')}
210
+ }
211
+
212
+ ${chalk.bold('Display Configuration (vv.display):')}
213
+ ${chalk.cyan('"display"')}: {
214
+ "layout": "manual", ${chalk.dim('// manual, hierarchical, force-directed')}
215
+ "theme": {
216
+ "primary": "#3b82f6",
217
+ "success": "#22c55e",
218
+ "warning": "#f59e0b",
219
+ "danger": "#ef4444"
220
+ },
221
+ "animations": {
222
+ "enabled": true,
223
+ "speed": 1.0
224
+ }
225
+ }
226
+ `,
227
+ examples: `
228
+ ${chalk.bold.cyan('Example Configurations')}
229
+ ${chalk.dim('═'.repeat(50))}
230
+
231
+ ${chalk.bold('Minimal Valid Canvas:')}
232
+ ${chalk.dim('─'.repeat(50))}
233
+ {
234
+ "nodes": [
235
+ {
236
+ "id": "node-1",
237
+ "type": "text",
238
+ "x": 100, "y": 100,
239
+ "width": 150, "height": 80,
240
+ "text": "Hello World"
241
+ }
242
+ ],
243
+ "edges": [],
244
+ "pv": {
245
+ "name": "My Graph",
246
+ "version": "1.0.0"
247
+ }
248
+ }
249
+
250
+ ${chalk.bold('Service Architecture:')}
251
+ ${chalk.dim('─'.repeat(50))}
252
+ {
253
+ "nodes": [
254
+ {
255
+ "id": "api",
256
+ "type": "text",
257
+ "x": 100, "y": 100,
258
+ "width": 150, "height": 80,
259
+ "text": "API Gateway",
260
+ "pv": {
261
+ "nodeType": "service",
262
+ "shape": "rectangle",
263
+ "fill": "#3b82f6",
264
+ "stroke": "#1d4ed8",
265
+ "icon": "Server",
266
+ "sources": ["src/api/**/*.ts"]
267
+ }
268
+ },
269
+ {
270
+ "id": "db",
271
+ "type": "text",
272
+ "x": 350, "y": 100,
273
+ "width": 150, "height": 80,
274
+ "text": "Database",
275
+ "pv": {
276
+ "nodeType": "database",
277
+ "shape": "hexagon",
278
+ "fill": "#8b5cf6",
279
+ "stroke": "#6d28d9",
280
+ "icon": "Database"
281
+ }
282
+ }
283
+ ],
284
+ "edges": [
285
+ {
286
+ "id": "api-to-db",
287
+ "fromNode": "api",
288
+ "toNode": "db",
289
+ "pv": { "edgeType": "query" }
290
+ }
291
+ ],
292
+ "pv": {
293
+ "name": "Service Architecture",
294
+ "version": "1.0.0",
295
+ "edgeTypes": {
296
+ "query": {
297
+ "style": "solid",
298
+ "color": "#64748b",
299
+ "width": 2,
300
+ "animation": {
301
+ "type": "flow",
302
+ "duration": 1500
303
+ }
304
+ }
305
+ }
306
+ }
307
+ }
308
+
309
+ ${chalk.bold('Run validation:')} ${chalk.cyan('privu validate <file>')}
310
+ ${chalk.bold('Initialize project:')} ${chalk.cyan('privu init')}
311
+ `,
312
+ };
313
+ export function createSchemaCommand() {
314
+ const command = new Command('schema');
315
+ command
316
+ .description('Display documentation about the canvas schema')
317
+ .argument('[section]', 'Section to display: overview, nodes, edges, vv, examples')
318
+ .action((section) => {
319
+ const validSections = Object.keys(SCHEMA_SECTIONS);
320
+ if (!section) {
321
+ console.log(SCHEMA_SECTIONS.overview);
322
+ return;
323
+ }
324
+ const normalizedSection = section.toLowerCase();
325
+ if (!validSections.includes(normalizedSection)) {
326
+ console.log(chalk.red(`Unknown section: ${section}`));
327
+ console.log(`Valid sections: ${validSections.join(', ')}`);
328
+ process.exit(1);
329
+ }
330
+ console.log(SCHEMA_SECTIONS[normalizedSection]);
331
+ });
332
+ return command;
333
+ }
@@ -0,0 +1,6 @@
1
+ /**
2
+ * Validate command - Validate .canvas configuration files
3
+ */
4
+ import { Command } from 'commander';
5
+ export declare function createValidateCommand(): Command;
6
+ //# sourceMappingURL=validate.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"validate.d.ts","sourceRoot":"","sources":["../../src/commands/validate.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAoVpC,wBAAgB,qBAAqB,IAAI,OAAO,CAyF/C"}