@principal-ai/principal-view-cli 0.2.2 → 0.2.4

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/index.cjs CHANGED
@@ -228612,7 +228612,7 @@ var ALLOWED_CANVAS_FIELDS = {
228612
228612
  "name",
228613
228613
  "description",
228614
228614
  "otel",
228615
- "events",
228615
+ "event",
228616
228616
  "shape",
228617
228617
  "icon",
228618
228618
  "fill",
@@ -228735,7 +228735,7 @@ function hasOtelFeatures(canvas) {
228735
228735
  if (nodePv.otel !== void 0) {
228736
228736
  return true;
228737
228737
  }
228738
- if (nodePv.events !== void 0) {
228738
+ if (nodePv.event !== void 0) {
228739
228739
  return true;
228740
228740
  }
228741
228741
  if (nodePv.resourceMatch !== void 0) {
@@ -229019,7 +229019,17 @@ function validateCanvas(canvas, filePath, library, repositoryPath) {
229019
229019
  issues
229020
229020
  );
229021
229021
  }
229022
- const hasOtelFeatures2 = nodePv.otel !== void 0 || nodePv.events !== void 0;
229022
+ if (filePath.endsWith(".otel.canvas") && nodeType !== "group") {
229023
+ if (nodePv.event === void 0) {
229024
+ issues.push({
229025
+ type: "error",
229026
+ message: `Node "${nodeLabel}" in .otel.canvas file must have "pv.event" field`,
229027
+ path: `${nodePath2}.pv.event`,
229028
+ suggestion: 'Add event name, e.g.: "event": "user.login" or "event": "order.created"'
229029
+ });
229030
+ }
229031
+ }
229032
+ const hasOtelFeatures2 = nodePv.otel !== void 0 || nodePv.event !== void 0;
229023
229033
  if (hasOtelFeatures2) {
229024
229034
  if (!Array.isArray(nodePv.sources) || nodePv.sources.length === 0) {
229025
229035
  issues.push({
@@ -229029,6 +229039,14 @@ function validateCanvas(canvas, filePath, library, repositoryPath) {
229029
229039
  suggestion: 'Add at least one source file reference, e.g.: "sources": ["src/services/MyService.ts"]'
229030
229040
  });
229031
229041
  }
229042
+ if (filePath.endsWith(".otel.canvas") && nodePv.event !== void 0 && nodePv.otel === void 0) {
229043
+ issues.push({
229044
+ type: "error",
229045
+ message: `Node "${nodeLabel}" in .otel.canvas file has event but is missing "pv.otel" field required for UI badges`,
229046
+ path: `${nodePath2}.pv.otel`,
229047
+ suggestion: 'Add OTEL metadata for UI rendering, e.g.: "otel": { "kind": "event", "category": "lifecycle", "isNew": true }'
229048
+ });
229049
+ }
229032
229050
  }
229033
229051
  if (Array.isArray(nodePv.sources) && repositoryPath) {
229034
229052
  nodePv.sources.forEach((source, sourceIndex) => {
@@ -241111,6 +241129,478 @@ function createSchemaCommand() {
241111
241129
  return command;
241112
241130
  }
241113
241131
 
241132
+ // src/commands/formats.ts
241133
+ var FORMAT_SECTIONS = {
241134
+ overview: `
241135
+ ${source_default.bold.cyan("Principal View OTEL File Formats")}
241136
+ ${source_default.dim("\u2550".repeat(70))}
241137
+
241138
+ The Principal View OTEL workflow uses three main file types:
241139
+
241140
+ ${source_default.bold("1. Canvas Files")} ${source_default.yellow(".otel.canvas")}
241141
+ Define OTEL event schemas and telemetry structure for a feature.
241142
+ These are the single source of truth for what events should be emitted.
241143
+
241144
+ ${source_default.bold("2. Narrative Files")} ${source_default.yellow(".narrative.json")}
241145
+ Define scenarios and templates for rendering executions as human-readable
241146
+ narratives based on the emitted events.
241147
+
241148
+ ${source_default.bold("3. Execution Files")} ${source_default.yellow(".otel.json")}
241149
+ Captured OTEL spans from test runs or production code, exported for
241150
+ visualization and validation against canvas schemas.
241151
+
241152
+ Run ${source_default.cyan("npx @principal-ai/principal-view-cli formats <section>")} for details on:
241153
+ ${source_default.yellow("canvas")} .otel.canvas format and event schemas
241154
+ ${source_default.yellow("narrative")} .narrative.json format and scenario structure
241155
+ ${source_default.yellow("execution")} .otel.json format for captured spans
241156
+ ${source_default.yellow("examples")} Complete example files
241157
+ `,
241158
+ canvas: `
241159
+ ${source_default.bold.cyan("Canvas Format (.otel.canvas)")}
241160
+ ${source_default.dim("\u2550".repeat(70))}
241161
+
241162
+ Canvas files define the OTEL event schemas for a feature. They document what
241163
+ events should be emitted and what attributes each event must/may contain.
241164
+
241165
+ ${source_default.bold("File Location:")}
241166
+ ${source_default.dim(".principal-views/")}${source_default.yellow("<feature-name>.otel.canvas")}
241167
+
241168
+ ${source_default.bold("Required Structure:")}
241169
+ ${source_default.dim("\u250C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2510")}
241170
+ ${source_default.dim("\u2502")} { ${source_default.dim("\u2502")}
241171
+ ${source_default.dim("\u2502")} ${source_default.green('"nodes"')}: [ ${source_default.dim("// Array of event schemas")} ${source_default.dim("\u2502")}
241172
+ ${source_default.dim("\u2502")} { ${source_default.dim("\u2502")}
241173
+ ${source_default.dim("\u2502")} ${source_default.yellow('"id"')}: "event-id", ${source_default.dim("// Unique identifier")} ${source_default.dim("\u2502")}
241174
+ ${source_default.dim("\u2502")} ${source_default.yellow('"type"')}: "text", ${source_default.dim("\u2502")}
241175
+ ${source_default.dim("\u2502")} ${source_default.yellow('"text"')}: "# Event Name", ${source_default.dim("// Markdown description")} ${source_default.dim("\u2502")}
241176
+ ${source_default.dim("\u2502")} ${source_default.yellow('"x"')}: 0, ${source_default.yellow('"y"')}: 0, ${source_default.yellow('"width"')}: 200, ${source_default.yellow('"height"')}: 100, ${source_default.dim("\u2502")}
241177
+ ${source_default.dim("\u2502")} ${source_default.green('"pv"')}: { ${source_default.dim("\u2502")}
241178
+ ${source_default.dim("\u2502")} ${source_default.cyan('"otelEvent"')}: { ${source_default.dim("// OTEL event definition")} ${source_default.dim("\u2502")}
241179
+ ${source_default.dim("\u2502")} ${source_default.yellow('"name"')}: "feature.event.name", ${source_default.dim("\u2502")}
241180
+ ${source_default.dim("\u2502")} ${source_default.cyan('"attributes"')}: { ${source_default.dim("// Required & optional attrs")} ${source_default.dim("\u2502")}
241181
+ ${source_default.dim("\u2502")} ${source_default.green('"required"')}: ["attr.name", ...], ${source_default.dim("\u2502")}
241182
+ ${source_default.dim("\u2502")} ${source_default.green('"optional"')}: ["attr.name", ...] ${source_default.dim("\u2502")}
241183
+ ${source_default.dim("\u2502")} } ${source_default.dim("\u2502")}
241184
+ ${source_default.dim("\u2502")} } ${source_default.dim("\u2502")}
241185
+ ${source_default.dim("\u2502")} } ${source_default.dim("\u2502")}
241186
+ ${source_default.dim("\u2502")} } ${source_default.dim("\u2502")}
241187
+ ${source_default.dim("\u2502")} ], ${source_default.dim("\u2502")}
241188
+ ${source_default.dim("\u2502")} ${source_default.green('"edges"')}: [], ${source_default.dim("// Optional: event relationships")} ${source_default.dim("\u2502")}
241189
+ ${source_default.dim("\u2502")} ${source_default.green('"pv"')}: { ${source_default.dim("\u2502")}
241190
+ ${source_default.dim("\u2502")} ${source_default.yellow('"name"')}: "Feature Name", ${source_default.dim('// Feature name (NOT "...Canvas")')} ${source_default.dim("\u2502")}
241191
+ ${source_default.dim("\u2502")} ${source_default.yellow('"version"')}: "1.0.0" ${source_default.dim("\u2502")}
241192
+ ${source_default.dim("\u2502")} } ${source_default.dim("\u2502")}
241193
+ ${source_default.dim("\u2502")} } ${source_default.dim("\u2502")}
241194
+ ${source_default.dim("\u2514\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2518")}
241195
+
241196
+ ${source_default.bold("Event Schema Best Practices:")}
241197
+
241198
+ ${source_default.cyan("1. Canvas represents complete, encompassing functionality:")}
241199
+ \u2705 API route - Full request/response cycle
241200
+ \u2705 CLI command - Complete tool execution
241201
+ \u2705 Business operation - End-to-end workflow
241202
+ \u274C Individual helper functions (too granular)
241203
+
241204
+ ${source_default.cyan("2. Event naming convention:")}
241205
+ ${source_default.yellow("<feature>.<operation>.<state>")}
241206
+ Examples:
241207
+ - validation.started
241208
+ - validation.complete
241209
+ - validation.error
241210
+ - import.parsing.complete
241211
+
241212
+ ${source_default.cyan("3. Start simple (2-4 events):")}
241213
+ - ${source_default.green("started")} - When feature begins
241214
+ - ${source_default.green("complete")} - When feature succeeds
241215
+ - ${source_default.green("error")} - When feature fails
241216
+ - (optional) progress events for clear intermediate steps
241217
+
241218
+ ${source_default.cyan("4. Attribute naming conventions:")}
241219
+ ${source_default.yellow("<category>.<name>")}
241220
+ - input.* (input.size, input.recordCount)
241221
+ - output.* (output.count, output.success)
241222
+ - result.* (result.validCount, result.invalidCount)
241223
+ - error.* (error.type, error.message, error.stage)
241224
+ - duration.* (duration.ms)
241225
+
241226
+ ${source_default.cyan("5. Required vs Optional attributes:")}
241227
+ - ${source_default.green("required")}: Essential data needed for validation
241228
+ - ${source_default.yellow("optional")}: Nice-to-have context, won't fail validation if missing
241229
+
241230
+ ${source_default.bold("Validation:")}
241231
+ ${source_default.cyan("npx @principal-ai/principal-view-cli validate")}
241232
+ `,
241233
+ narrative: `
241234
+ ${source_default.bold.cyan("Narrative Format (.narrative.json)")}
241235
+ ${source_default.dim("\u2550".repeat(70))}
241236
+
241237
+ Narrative files define scenarios for rendering execution data as human-readable
241238
+ stories. They evaluate conditions against captured events to select the best
241239
+ matching narrative template.
241240
+
241241
+ ${source_default.bold("File Location:")}
241242
+ ${source_default.dim(".principal-views/")}${source_default.yellow("<feature-name>.narrative.json")}
241243
+ ${source_default.dim("(co-located with corresponding .otel.canvas file)")}
241244
+
241245
+ ${source_default.bold("Required Structure:")}
241246
+ ${source_default.dim("\u250C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2510")}
241247
+ ${source_default.dim("\u2502")} { ${source_default.dim("\u2502")}
241248
+ ${source_default.dim("\u2502")} ${source_default.green('"name"')}: "Feature Name", ${source_default.dim('// NOT "Feature Name Narratives"')} ${source_default.dim("\u2502")}
241249
+ ${source_default.dim("\u2502")} ${source_default.green('"description"')}: "What the feature does", ${source_default.dim('// Purpose, not "Narratives for..."')} ${source_default.dim("\u2502")}
241250
+ ${source_default.dim("\u2502")} ${source_default.green('"scenarios"')}: [ ${source_default.dim("\u2502")}
241251
+ ${source_default.dim("\u2502")} { ${source_default.dim("\u2502")}
241252
+ ${source_default.dim("\u2502")} ${source_default.yellow('"priority"')}: 1, ${source_default.dim("// Lower = higher priority")} ${source_default.dim("\u2502")}
241253
+ ${source_default.dim("\u2502")} ${source_default.yellow('"condition"')}: "...", ${source_default.dim("// JSONPath/logic expression")} ${source_default.dim("\u2502")}
241254
+ ${source_default.dim("\u2502")} ${source_default.yellow('"template"')}: { ${source_default.dim("// Narrative template")} ${source_default.dim("\u2502")}
241255
+ ${source_default.dim("\u2502")} ${source_default.cyan('"summary"')}: "...", ${source_default.dim("// One-line summary")} ${source_default.dim("\u2502")}
241256
+ ${source_default.dim("\u2502")} ${source_default.cyan('"details"')}: [ ${source_default.dim("// Step-by-step details")} ${source_default.dim("\u2502")}
241257
+ ${source_default.dim("\u2502")} "Step 1: ...", ${source_default.dim("\u2502")}
241258
+ ${source_default.dim("\u2502")} "Step 2: ...", ${source_default.dim("\u2502")}
241259
+ ${source_default.dim("\u2502")} ] ${source_default.dim("\u2502")}
241260
+ ${source_default.dim("\u2502")} } ${source_default.dim("\u2502")}
241261
+ ${source_default.dim("\u2502")} } ${source_default.dim("\u2502")}
241262
+ ${source_default.dim("\u2502")} ] ${source_default.dim("\u2502")}
241263
+ ${source_default.dim("\u2502")} } ${source_default.dim("\u2502")}
241264
+ ${source_default.dim("\u2514\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2518")}
241265
+
241266
+ ${source_default.bold("Naming Guidelines:")}
241267
+
241268
+ \u274C DON'T append "Narratives" to the name:
241269
+ "name": "Package Processor Narratives"
241270
+
241271
+ \u2705 DO use the feature name directly:
241272
+ "name": "Package Processor"
241273
+
241274
+ \u274C DON'T prefix description with boilerplate:
241275
+ "description": "Human-readable narratives for package extraction..."
241276
+
241277
+ \u2705 DO describe the feature's purpose:
241278
+ "description": "Package extraction and analysis from repository file trees"
241279
+
241280
+ ${source_default.bold("Scenario Best Practices:")}
241281
+
241282
+ ${source_default.cyan("1. Priority ordering (scenarios evaluated in order):")}
241283
+ - ${source_default.green("1-10")} Specific scenarios (success/failure cases)
241284
+ - ${source_default.yellow("999")} Fallback scenario (catches anything)
241285
+
241286
+ ${source_default.cyan("2. Standard scenario set:")}
241287
+ - ${source_default.green("Success")} (priority 1): Feature completed successfully
241288
+ - ${source_default.yellow("Failure")} (priority 2): Feature encountered error
241289
+ - ${source_default.dim("Fallback")} (priority 999): Generic execution captured
241290
+
241291
+ ${source_default.cyan("3. Template interpolation:")}
241292
+ Use {{path.to.value}} to reference event attributes
241293
+ Examples:
241294
+ - {{record.count}}
241295
+ - {{error.message}}
241296
+ - {{result.invalidCount}}
241297
+
241298
+ ${source_default.cyan("4. Template style:")}
241299
+ - Clear, concise summary line
241300
+ - 3-5 detail steps showing workflow
241301
+ - Use emojis for visual scanning (\u2705 \u274C \u{1F4CB})
241302
+ - Include key metrics and IDs
241303
+
241304
+ ${source_default.bold("Validation:")}
241305
+ ${source_default.cyan("npx @principal-ai/principal-view-cli narrative validate")}
241306
+ `,
241307
+ execution: `
241308
+ ${source_default.bold.cyan("Execution Format (.otel.json)")}
241309
+ ${source_default.dim("\u2550".repeat(70))}
241310
+
241311
+ Execution files contain captured OTEL spans from test runs or production code.
241312
+ These files are exported by your test infrastructure and used for visualization
241313
+ and validation against canvas schemas.
241314
+
241315
+ ${source_default.bold("File Location:")}
241316
+ ${source_default.yellow("__executions__/")}${source_default.dim("<feature-name>.otel.json")}
241317
+ ${source_default.dim("(auto-generated by test infrastructure)")}
241318
+
241319
+ ${source_default.bold("IMPORTANT:")} __executions__/ directory must be committed to git!
241320
+
241321
+ ${source_default.bold("File Structure:")}
241322
+ ${source_default.dim("\u250C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2510")}
241323
+ ${source_default.dim("\u2502")} { ${source_default.dim("\u2502")}
241324
+ ${source_default.dim("\u2502")} ${source_default.green('"exportedAt"')}: "2025-01-21T10:30:00.000Z", ${source_default.dim("// ISO timestamp")} ${source_default.dim("\u2502")}
241325
+ ${source_default.dim("\u2502")} ${source_default.green('"serviceName"')}: "my-service", ${source_default.dim("// Service name")} ${source_default.dim("\u2502")}
241326
+ ${source_default.dim("\u2502")} ${source_default.green('"spanCount"')}: 5, ${source_default.dim("// Total spans")} ${source_default.dim("\u2502")}
241327
+ ${source_default.dim("\u2502")} ${source_default.green('"spans"')}: [ ${source_default.dim("\u2502")}
241328
+ ${source_default.dim("\u2502")} { ${source_default.dim("\u2502")}
241329
+ ${source_default.dim("\u2502")} ${source_default.yellow('"traceId"')}: "4bf92f3577b34da6...", ${source_default.dim("// 32 hex chars")} ${source_default.dim("\u2502")}
241330
+ ${source_default.dim("\u2502")} ${source_default.yellow('"spanId"')}: "00f067aa0ba902b7", ${source_default.dim("// 16 hex chars")} ${source_default.dim("\u2502")}
241331
+ ${source_default.dim("\u2502")} ${source_default.yellow('"parentSpanId"')}: "abc123...", ${source_default.dim("// Parent span (null for root)")} ${source_default.dim("\u2502")}
241332
+ ${source_default.dim("\u2502")} ${source_default.yellow('"name"')}: "test:feature-name", ${source_default.dim("// Span name")} ${source_default.dim("\u2502")}
241333
+ ${source_default.dim("\u2502")} ${source_default.yellow('"kind"')}: "INTERNAL", ${source_default.dim("// Span kind")} ${source_default.dim("\u2502")}
241334
+ ${source_default.dim("\u2502")} ${source_default.yellow('"startTime"')}: 1703548800000, ${source_default.dim("// Unix ms")} ${source_default.dim("\u2502")}
241335
+ ${source_default.dim("\u2502")} ${source_default.yellow('"endTime"')}: 1703548800050, ${source_default.dim("// Unix ms")} ${source_default.dim("\u2502")}
241336
+ ${source_default.dim("\u2502")} ${source_default.yellow('"duration"')}: 50, ${source_default.dim("// Duration in ms")} ${source_default.dim("\u2502")}
241337
+ ${source_default.dim("\u2502")} ${source_default.yellow('"attributes"')}: { ${source_default.dim("// Event attributes")} ${source_default.dim("\u2502")}
241338
+ ${source_default.dim("\u2502")} "input.size": 42, ${source_default.dim("\u2502")}
241339
+ ${source_default.dim("\u2502")} "output.success": true ${source_default.dim("\u2502")}
241340
+ ${source_default.dim("\u2502")} }, ${source_default.dim("\u2502")}
241341
+ ${source_default.dim("\u2502")} ${source_default.yellow('"status"')}: { ${source_default.dim("\u2502")}
241342
+ ${source_default.dim("\u2502")} "code": "OK" ${source_default.dim("// OK, ERROR, UNSET")} ${source_default.dim("\u2502")}
241343
+ ${source_default.dim("\u2502")} }, ${source_default.dim("\u2502")}
241344
+ ${source_default.dim("\u2502")} ${source_default.yellow('"events"')}: [] ${source_default.dim("// Optional span events")} ${source_default.dim("\u2502")}
241345
+ ${source_default.dim("\u2502")} } ${source_default.dim("\u2502")}
241346
+ ${source_default.dim("\u2502")} ] ${source_default.dim("\u2502")}
241347
+ ${source_default.dim("\u2502")} } ${source_default.dim("\u2502")}
241348
+ ${source_default.dim("\u2514\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2518")}
241349
+
241350
+ ${source_default.bold("Field Descriptions:")}
241351
+
241352
+ ${source_default.cyan("exportedAt")} ${source_default.dim("(string, required)")}
241353
+ ISO 8601 timestamp when the file was exported
241354
+
241355
+ ${source_default.cyan("serviceName")} ${source_default.dim("(string, required)")}
241356
+ Name of the service/test suite that generated these spans
241357
+
241358
+ ${source_default.cyan("spanCount")} ${source_default.dim("(number, required)")}
241359
+ Total number of spans in this execution
241360
+
241361
+ ${source_default.cyan("spans")} ${source_default.dim("(array, required)")}
241362
+ Array of span objects containing OTEL trace data
241363
+
241364
+ ${source_default.bold("Span Object Fields:")}
241365
+
241366
+ ${source_default.cyan("traceId")} ${source_default.dim("(string, 32 hex chars)")}
241367
+ Unique identifier for the entire trace
241368
+
241369
+ ${source_default.cyan("spanId")} ${source_default.dim("(string, 16 hex chars)")}
241370
+ Unique identifier for this specific span
241371
+
241372
+ ${source_default.cyan("parentSpanId")} ${source_default.dim("(string | null)")}
241373
+ Parent span ID, or null for root span
241374
+
241375
+ ${source_default.cyan("name")} ${source_default.dim("(string)")}
241376
+ Descriptive name for the operation
241377
+
241378
+ ${source_default.cyan("kind")} ${source_default.dim("(string)")}
241379
+ Span kind: INTERNAL, CLIENT, SERVER, PRODUCER, CONSUMER
241380
+
241381
+ ${source_default.cyan("startTime")} ${source_default.dim("(number)")}
241382
+ Unix timestamp in milliseconds when span started
241383
+
241384
+ ${source_default.cyan("endTime")} ${source_default.dim("(number)")}
241385
+ Unix timestamp in milliseconds when span ended
241386
+
241387
+ ${source_default.cyan("duration")} ${source_default.dim("(number)")}
241388
+ Duration in milliseconds (endTime - startTime)
241389
+
241390
+ ${source_default.cyan("attributes")} ${source_default.dim("(object)")}
241391
+ Key-value pairs of event attributes (validated against canvas schema)
241392
+
241393
+ ${source_default.cyan("status")} ${source_default.dim("(object)")}
241394
+ Status code (OK, ERROR, UNSET) and optional message
241395
+
241396
+ ${source_default.cyan("events")} ${source_default.dim("(array)")}
241397
+ Optional array of timestamped events within the span
241398
+
241399
+ ${source_default.bold("Generation:")}
241400
+ Set up test infrastructure with OTEL exporters that write to __executions__/
241401
+ See: docs/guides/adding-opentelemetry-to-tests.md
241402
+
241403
+ ${source_default.bold("Validation:")}
241404
+ ${source_default.cyan("npx @principal-ai/principal-view-cli validate-execution <file>")}
241405
+ `,
241406
+ examples: `
241407
+ ${source_default.bold.cyan("Complete File Examples")}
241408
+ ${source_default.dim("\u2550".repeat(70))}
241409
+
241410
+ ${source_default.bold("Example 1: Data Validator Canvas")}
241411
+ ${source_default.dim("\u2500".repeat(70))}
241412
+ ${source_default.yellow(".principal-views/data-validator.otel.canvas")}
241413
+
241414
+ {
241415
+ "nodes": [
241416
+ {
241417
+ "id": "validation-started",
241418
+ "type": "text",
241419
+ "text": "# validation.started\\n\\nEmitted when validation begins",
241420
+ "x": 0, "y": 0, "width": 200, "height": 100,
241421
+ "pv": {
241422
+ "otelEvent": {
241423
+ "name": "validation.started",
241424
+ "attributes": {
241425
+ "required": ["input.recordCount"],
241426
+ "optional": ["input.source"]
241427
+ }
241428
+ }
241429
+ }
241430
+ },
241431
+ {
241432
+ "id": "validation-complete",
241433
+ "type": "text",
241434
+ "text": "# validation.complete\\n\\nEmitted when validation succeeds",
241435
+ "x": 250, "y": 0, "width": 200, "height": 100,
241436
+ "pv": {
241437
+ "otelEvent": {
241438
+ "name": "validation.complete",
241439
+ "attributes": {
241440
+ "required": ["result.validCount", "result.invalidCount"],
241441
+ "optional": ["duration.ms"]
241442
+ }
241443
+ }
241444
+ }
241445
+ },
241446
+ {
241447
+ "id": "validation-error",
241448
+ "type": "text",
241449
+ "text": "# validation.error\\n\\nEmitted when validation fails",
241450
+ "x": 500, "y": 0, "width": 200, "height": 100,
241451
+ "pv": {
241452
+ "otelEvent": {
241453
+ "name": "validation.error",
241454
+ "attributes": {
241455
+ "required": ["error.type", "error.message"],
241456
+ "optional": ["error.stage"]
241457
+ }
241458
+ }
241459
+ }
241460
+ }
241461
+ ],
241462
+ "edges": [],
241463
+ "pv": {
241464
+ "name": "Data Validator",
241465
+ "version": "1.0.0"
241466
+ }
241467
+ }
241468
+
241469
+ ${source_default.bold("Example 2: Narrative Scenarios")}
241470
+ ${source_default.dim("\u2500".repeat(70))}
241471
+ ${source_default.yellow(".principal-views/data-validator.narrative.json")}
241472
+
241473
+ {
241474
+ "name": "Data Validator",
241475
+ "description": "Validates data records against defined schemas",
241476
+ "scenarios": [
241477
+ {
241478
+ "priority": 1,
241479
+ "condition": "events[?name=='validation.complete']",
241480
+ "template": {
241481
+ "summary": "\u2705 Validated {{result.validCount}} records successfully",
241482
+ "details": [
241483
+ "\u{1F50D} Started validation",
241484
+ "\u{1F4CA} Processed {{input.recordCount}} records",
241485
+ "\u2705 {{result.validCount}} valid",
241486
+ "\u274C {{result.invalidCount}} invalid"
241487
+ ]
241488
+ }
241489
+ },
241490
+ {
241491
+ "priority": 2,
241492
+ "condition": "events[?name=='validation.error']",
241493
+ "template": {
241494
+ "summary": "\u274C Validation failed: {{error.message}}",
241495
+ "details": [
241496
+ "\u{1F50D} Started validation",
241497
+ "\u{1F4A5} Error occurred: {{error.message}}",
241498
+ "\u{1F3F7}\uFE0F Error type: {{error.type}}"
241499
+ ]
241500
+ }
241501
+ },
241502
+ {
241503
+ "priority": 999,
241504
+ "condition": "true",
241505
+ "template": {
241506
+ "summary": "\u{1F4CB} Validation execution captured",
241507
+ "details": [
241508
+ "\u{1F4E6} Captured {{spans.length}} events",
241509
+ "\u23F1\uFE0F Duration: {{duration.ms}}ms"
241510
+ ]
241511
+ }
241512
+ }
241513
+ ]
241514
+ }
241515
+
241516
+ ${source_default.bold("Example 3: Execution File")}
241517
+ ${source_default.dim("\u2500".repeat(70))}
241518
+ ${source_default.yellow("__executions__/data-validator.otel.json")}
241519
+
241520
+ {
241521
+ "exportedAt": "2025-01-21T10:30:45.123Z",
241522
+ "serviceName": "my-app-tests",
241523
+ "spanCount": 3,
241524
+ "spans": [
241525
+ {
241526
+ "traceId": "4bf92f3577b34da6a3ce929d0e0e4736",
241527
+ "spanId": "00f067aa0ba902b7",
241528
+ "parentSpanId": null,
241529
+ "name": "test:data-validator",
241530
+ "kind": "INTERNAL",
241531
+ "startTime": 1703548800000,
241532
+ "endTime": 1703548800150,
241533
+ "duration": 150,
241534
+ "attributes": {
241535
+ "test.name": "data validator success case"
241536
+ },
241537
+ "status": { "code": "OK" },
241538
+ "events": []
241539
+ },
241540
+ {
241541
+ "traceId": "4bf92f3577b34da6a3ce929d0e0e4736",
241542
+ "spanId": "abc123def4567890",
241543
+ "parentSpanId": "00f067aa0ba902b7",
241544
+ "name": "validation.started",
241545
+ "kind": "INTERNAL",
241546
+ "startTime": 1703548800010,
241547
+ "endTime": 1703548800015,
241548
+ "duration": 5,
241549
+ "attributes": {
241550
+ "input.recordCount": 100,
241551
+ "input.source": "test-data.csv"
241552
+ },
241553
+ "status": { "code": "OK" },
241554
+ "events": []
241555
+ },
241556
+ {
241557
+ "traceId": "4bf92f3577b34da6a3ce929d0e0e4736",
241558
+ "spanId": "def789abc1234567",
241559
+ "parentSpanId": "00f067aa0ba902b7",
241560
+ "name": "validation.complete",
241561
+ "kind": "INTERNAL",
241562
+ "startTime": 1703548800140,
241563
+ "endTime": 1703548800145,
241564
+ "duration": 5,
241565
+ "attributes": {
241566
+ "result.validCount": 95,
241567
+ "result.invalidCount": 5,
241568
+ "duration.ms": 130
241569
+ },
241570
+ "status": { "code": "OK" },
241571
+ "events": []
241572
+ }
241573
+ ]
241574
+ }
241575
+
241576
+ ${source_default.bold("Next Steps:")}
241577
+ ${source_default.cyan("npx @principal-ai/principal-view-cli validate")} Validate canvas
241578
+ ${source_default.cyan("npx @principal-ai/principal-view-cli narrative validate")} Validate narratives
241579
+ ${source_default.cyan("npx @principal-ai/principal-view-cli validate-execution")} Validate execution
241580
+ `
241581
+ };
241582
+ function createFormatsCommand() {
241583
+ const command = new Command("formats");
241584
+ command.description("Display documentation about file formats").argument(
241585
+ "[section]",
241586
+ "Section to display: overview, canvas, narrative, execution, examples"
241587
+ ).action((section) => {
241588
+ const validSections = Object.keys(FORMAT_SECTIONS);
241589
+ if (!section) {
241590
+ console.log(FORMAT_SECTIONS.overview);
241591
+ return;
241592
+ }
241593
+ const normalizedSection = section.toLowerCase();
241594
+ if (!validSections.includes(normalizedSection)) {
241595
+ console.log(source_default.red(`Unknown section: ${section}`));
241596
+ console.log(`Valid sections: ${validSections.join(", ")}`);
241597
+ process.exit(1);
241598
+ }
241599
+ console.log(FORMAT_SECTIONS[normalizedSection]);
241600
+ });
241601
+ return command;
241602
+ }
241603
+
241114
241604
  // src/commands/doctor.ts
241115
241605
  var import_node_fs8 = require("node:fs");
241116
241606
  var import_node_path9 = require("node:path");
@@ -242919,7 +243409,7 @@ function createNarrativeCommand() {
242919
243409
  }
242920
243410
 
242921
243411
  // src/index.ts
242922
- var VERSION2 = "0.2.1";
243412
+ var VERSION2 = "0.2.3";
242923
243413
  var program2 = new Command();
242924
243414
  program2.name("privu").description("Principal View CLI - Validate and manage .canvas configuration files").version(VERSION2);
242925
243415
  program2.addCommand(createInitCommand());
@@ -242929,6 +243419,7 @@ program2.addCommand(createValidateExecutionCommand());
242929
243419
  program2.addCommand(createLintCommand());
242930
243420
  program2.addCommand(createListCommand());
242931
243421
  program2.addCommand(createSchemaCommand());
243422
+ program2.addCommand(createFormatsCommand());
242932
243423
  program2.addCommand(createDoctorCommand());
242933
243424
  program2.addCommand(createHooksCommand());
242934
243425
  program2.addCommand(createCoverageCommand());