agent-inspect 6.8.0 → 6.10.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.
Files changed (41) hide show
  1. package/CHANGELOG.md +12 -0
  2. package/README.md +1 -1
  3. package/docs/BUNDLES.md +31 -9
  4. package/docs/CI-ARTIFACTS.md +10 -1
  5. package/docs/CLI.md +20 -4
  6. package/package.json +1 -1
  7. package/packages/cli/dist/{chunk-TO4VENHV.mjs → chunk-36IJ76LH.mjs} +1857 -158
  8. package/packages/cli/dist/chunk-36IJ76LH.mjs.map +1 -0
  9. package/packages/cli/dist/index.cjs +10764 -8877
  10. package/packages/cli/dist/index.cjs.map +1 -1
  11. package/packages/cli/dist/index.mjs +825 -754
  12. package/packages/cli/dist/index.mjs.map +1 -1
  13. package/packages/cli/dist/{src-Z5W27YCW.mjs → src-YFN3Q3GP.mjs} +3 -3
  14. package/packages/cli/dist/{src-Z5W27YCW.mjs.map → src-YFN3Q3GP.mjs.map} +1 -1
  15. package/packages/core/dist/advanced.cjs +1718 -18
  16. package/packages/core/dist/advanced.cjs.map +1 -1
  17. package/packages/core/dist/advanced.d.cts +338 -4
  18. package/packages/core/dist/advanced.d.ts +338 -4
  19. package/packages/core/dist/advanced.mjs +1166 -12
  20. package/packages/core/dist/advanced.mjs.map +1 -1
  21. package/packages/core/dist/checks.cjs +105 -14
  22. package/packages/core/dist/checks.cjs.map +1 -1
  23. package/packages/core/dist/checks.d.cts +2 -2
  24. package/packages/core/dist/checks.d.ts +2 -2
  25. package/packages/core/dist/checks.mjs +1 -1
  26. package/packages/core/dist/chunk-F7STQ5JF.mjs +479 -0
  27. package/packages/core/dist/chunk-F7STQ5JF.mjs.map +1 -0
  28. package/packages/core/dist/{chunk-EQVXDGGU.mjs → chunk-QT6CQ2XA.mjs} +107 -16
  29. package/packages/core/dist/chunk-QT6CQ2XA.mjs.map +1 -0
  30. package/packages/core/dist/diff.mjs +3 -477
  31. package/packages/core/dist/diff.mjs.map +1 -1
  32. package/packages/core/dist/{index-BblJEdYZ.d.ts → index-BO7l0iAe.d.ts} +44 -1
  33. package/packages/core/dist/{index-DyKk7iR9.d.cts → index-mdFcxSOR.d.cts} +44 -1
  34. package/packages/core/dist/reporters.cjs +25 -0
  35. package/packages/core/dist/reporters.cjs.map +1 -1
  36. package/packages/core/dist/reporters.d.cts +16 -2
  37. package/packages/core/dist/reporters.d.ts +16 -2
  38. package/packages/core/dist/reporters.mjs +24 -1
  39. package/packages/core/dist/reporters.mjs.map +1 -1
  40. package/packages/cli/dist/chunk-TO4VENHV.mjs.map +0 -1
  41. package/packages/core/dist/chunk-EQVXDGGU.mjs.map +0 -1
@@ -17,6 +17,20 @@ type TraceCheckSeverity = "error" | "warning" | "info";
17
17
  * evolve during the v1.x experimental period.
18
18
  */
19
19
  type TraceCheckRuleCategory = "run" | "tool" | "llm" | "structure" | "baseline" | "safety" | "reader";
20
+ /**
21
+ * Experimental safety finding taxonomy (additive on `TraceCheckFinding`).
22
+ *
23
+ * Distinct from `TraceCheckRuleCategory` (which classifies rules, not findings).
24
+ *
25
+ * @experimental Available through `agent-inspect/checks`; see `docs/SAFETY-POLICY.md`.
26
+ */
27
+ type SafetyFindingCategory = "credential" | "personal-data" | "identifier" | "raw-content" | "path" | "size" | "structure";
28
+ /**
29
+ * Experimental detector confidence for safety findings.
30
+ *
31
+ * @experimental Available through `agent-inspect/checks`; see `docs/SAFETY-POLICY.md`.
32
+ */
33
+ type SafetyFindingConfidence = "high" | "medium" | "low";
20
34
  /**
21
35
  * Experimental trace-check finding status.
22
36
  *
@@ -72,6 +86,30 @@ interface TraceCheckFinding {
72
86
  expected?: unknown;
73
87
  actual?: unknown;
74
88
  evidence: TraceCheckEvidence[];
89
+ /**
90
+ * Additive safety taxonomy (6.9+). Omitted for non-safety / structural rules.
91
+ *
92
+ * @experimental
93
+ */
94
+ category?: SafetyFindingCategory;
95
+ /**
96
+ * Additive detector confidence (6.9+).
97
+ *
98
+ * @experimental
99
+ */
100
+ confidence?: SafetyFindingConfidence;
101
+ /**
102
+ * Detector id when known (rule id or redaction detector id).
103
+ *
104
+ * @experimental
105
+ */
106
+ detector?: string;
107
+ /**
108
+ * Recommended remediation action (e.g. redact, review, keep).
109
+ *
110
+ * @experimental
111
+ */
112
+ action?: string;
75
113
  }
76
114
  /**
77
115
  * Experimental diagnostic emitted when check execution cannot complete normally.
@@ -350,6 +388,11 @@ interface SafetyRedactionRuleOptions {
350
388
  */
351
389
  interface SafetyRawContentRuleOptions {
352
390
  forbiddenKeys?: readonly string[];
391
+ /**
392
+ * Path prefixes (dot-separated, case-insensitive) whose terminal keys are
393
+ * treated as metrics rather than raw prompts (e.g. `tokenUsage`, `usage`).
394
+ */
395
+ safePathPrefixes?: readonly string[];
353
396
  includeSummaries?: boolean;
354
397
  maxFindings?: number;
355
398
  }
@@ -615,4 +658,4 @@ declare function createObservedOutcomeRule(options?: ObservedOutcomeRuleOptions)
615
658
  */
616
659
  declare function runTraceChecks(input: TraceCheckInput, options?: RunTraceChecksOptions): TraceCheckResult;
617
660
 
618
- export { createSafetyRawContentRule as $, type TraceCheckRuleCategory as A, type BaselineRegressionRuleOptions as B, type TraceCheckSeverity as C, type DecisionRuleOptions as D, type TraceCheckStatus as E, type TraceCheckSummary as F, type GuardrailRuleOptions as G, type TraceSignalRuleOptions as H, createBaselineRegressionRule as I, createDecisionRule as J, createGuardrailRule as K, type LlmUsageRuleOptions as L, type MaxStepDurationRuleOptions as M, createLlmUsageRule as N, type ObservedOutcomeRuleOptions as O, createMaxStepDurationRule as P, createObservedOutcomeRule as Q, type RetrievalRuleOptions as R, type SafetyOversizedAttributeRuleOptions as S, type TraceCheckInput as T, createRequireCompletedRule as U, createRetrievalRule as V, createRunDepthRule as W, createRunDurationRule as X, createRunEventCountRule as Y, createRunStatusRule as Z, createSafetyOversizedAttributeRule as _, type TraceCheckResult as a, createSafetyRedactionRule as a0, createSafetySecretPatternRule as a1, createStallDetectionRule as a2, createStructureCycleRule as a3, createStructureIncompleteRule as a4, createStructureOrphanRule as a5, createStructureParallelWidthRule as a6, createStructureRelationshipRule as a7, createToolFailureRule as a8, createToolOrderingRule as a9, createToolUsageRule as aa, runTraceChecks as ab, type RunDepthRuleOptions as b, type RunDurationRuleOptions as c, type RunEventCountRuleOptions as d, type RunStatusRuleOptions as e, type RunTraceChecksOptions as f, type SafetyRawContentRuleOptions as g, type SafetyRedactionRuleOptions as h, type SafetySecretPattern as i, type SafetySecretPatternRuleOptions as j, type StallDetectionRuleOptions as k, type StructureIncompleteRuleOptions as l, type StructureOrphanRuleOptions as m, type StructureParallelWidthRuleOptions as n, type StructureRelationshipRuleOptions as o, type ToolFailureRuleOptions as p, type ToolOrderingRuleOptions as q, type ToolUsageRuleOptions as r, type TraceCheckContext as s, type TraceCheckDiagnostic as t, type TraceCheckDiagnosticCode as u, type TraceCheckEvidence as v, type TraceCheckFacts as w, type TraceCheckFinding as x, type TraceCheckFindingStatus as y, type TraceCheckRule as z };
661
+ export { createRunStatusRule as $, type TraceCheckFindingStatus as A, type BaselineRegressionRuleOptions as B, type TraceCheckRule as C, type DecisionRuleOptions as D, type TraceCheckRuleCategory as E, type TraceCheckSeverity as F, type GuardrailRuleOptions as G, type TraceCheckStatus as H, type TraceCheckSummary as I, type TraceSignalRuleOptions as J, createBaselineRegressionRule as K, type LlmUsageRuleOptions as L, type MaxStepDurationRuleOptions as M, createDecisionRule as N, type ObservedOutcomeRuleOptions as O, createGuardrailRule as P, createLlmUsageRule as Q, type RetrievalRuleOptions as R, type SafetyFindingCategory as S, type TraceCheckInput as T, createMaxStepDurationRule as U, createObservedOutcomeRule as V, createRequireCompletedRule as W, createRetrievalRule as X, createRunDepthRule as Y, createRunDurationRule as Z, createRunEventCountRule as _, type TraceCheckResult as a, createSafetyOversizedAttributeRule as a0, createSafetyRawContentRule as a1, createSafetyRedactionRule as a2, createSafetySecretPatternRule as a3, createStallDetectionRule as a4, createStructureCycleRule as a5, createStructureIncompleteRule as a6, createStructureOrphanRule as a7, createStructureParallelWidthRule as a8, createStructureRelationshipRule as a9, createToolFailureRule as aa, createToolOrderingRule as ab, createToolUsageRule as ac, runTraceChecks as ad, type RunDepthRuleOptions as b, type RunDurationRuleOptions as c, type RunEventCountRuleOptions as d, type RunStatusRuleOptions as e, type RunTraceChecksOptions as f, type SafetyFindingConfidence as g, type SafetyOversizedAttributeRuleOptions as h, type SafetyRawContentRuleOptions as i, type SafetyRedactionRuleOptions as j, type SafetySecretPattern as k, type SafetySecretPatternRuleOptions as l, type StallDetectionRuleOptions as m, type StructureIncompleteRuleOptions as n, type StructureOrphanRuleOptions as o, type StructureParallelWidthRuleOptions as p, type StructureRelationshipRuleOptions as q, type ToolFailureRuleOptions as r, type ToolOrderingRuleOptions as s, type ToolUsageRuleOptions as t, type TraceCheckContext as u, type TraceCheckDiagnostic as v, type TraceCheckDiagnosticCode as w, type TraceCheckEvidence as x, type TraceCheckFacts as y, type TraceCheckFinding as z };
@@ -175,8 +175,33 @@ function slugForPathLabel(value) {
175
175
  const slug = base.toLowerCase().replace(/[^a-z0-9._-]+/g, "-").replace(/^[._-]+|[._-]+$/g, "").slice(0, 80);
176
176
  return slug.length > 0 ? slug : "artifact";
177
177
  }
178
+ var EVIDENCE_CI_ARTIFACT_FILES = [
179
+ "evidence.html",
180
+ "evidence.json",
181
+ "check-results.json",
182
+ "trace.jsonl"
183
+ ];
184
+ function createEvidenceCiArtifacts(options) {
185
+ const profile = options.redactionProfile ?? "share";
186
+ const prefix = options.relativeDir !== void 0 && options.relativeDir.trim() !== "" ? options.relativeDir.replace(/\\/g, "/").replace(/^\/+|\/+$/g, "") : "";
187
+ const join = (name) => prefix === "" ? name : path__default.default.posix.join(prefix, name);
188
+ const formatFor = (name) => {
189
+ if (name.endsWith(".html")) return "html";
190
+ if (name.endsWith(".jsonl")) return "jsonl";
191
+ return "json";
192
+ };
193
+ return EVIDENCE_CI_ARTIFACT_FILES.map((name) => ({
194
+ kind: "evidence",
195
+ path: join(name),
196
+ format: formatFor(name),
197
+ redactionProfile: profile,
198
+ title: `Evidence v2 ${name}`
199
+ }));
200
+ }
178
201
 
202
+ exports.EVIDENCE_CI_ARTIFACT_FILES = EVIDENCE_CI_ARTIFACT_FILES;
179
203
  exports.TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION = TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION;
204
+ exports.createEvidenceCiArtifacts = createEvidenceCiArtifacts;
180
205
  exports.createReporterArtifactPath = createReporterArtifactPath;
181
206
  exports.createReporterFailureDiagnostic = createReporterFailureDiagnostic;
182
207
  exports.createTraceArtifactManifest = createTraceArtifactManifest;
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/reporters/index.ts"],"names":["path"],"mappings":"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","file":"reporters.cjs","sourcesContent":["import path from \"node:path\";\n\nexport const TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION = \"0.1\" as const;\n\n/** Experimental reporter framework identifier for local CI artifacts. */\nexport type TraceReporterFramework = \"vitest\" | \"jest\" | \"manual\";\n\n/** Experimental reporter test status normalized across supported test runners. */\nexport type TraceTestStatus = \"passed\" | \"failed\" | \"skipped\" | \"todo\";\n\n/** Experimental reporter artifact kind used in artifact manifests. */\nexport type TraceArtifactKind = \"trace\" | \"report\" | \"eval\" | \"redaction\" | \"summary\";\n\n/** Experimental reporter artifact file format used in artifact manifests. */\nexport type TraceArtifactFormat = \"json\" | \"jsonl\" | \"md\" | \"html\";\n\n/** Experimental redaction profile marker recorded with reporter artifacts. */\nexport type TraceArtifactRedactionProfile = \"local\" | \"share\" | \"strict\";\n\n/** Experimental reporter diagnostic severity. */\nexport type TraceReporterDiagnosticSeverity = \"info\" | \"warning\" | \"error\";\n\n/** Experimental reporter diagnostic code for safe, non-throwing reporter helpers. */\nexport type TraceReporterDiagnosticCode =\n | \"invalid_artifact_path\"\n | \"artifact_path_escape\"\n | \"artifact_path_empty\"\n | \"artifact_path_absolute\"\n | \"reporter_failure\";\n\n/** Experimental diagnostic emitted by reporter helpers instead of throwing. */\nexport interface TraceReporterDiagnostic {\n code: TraceReporterDiagnosticCode;\n severity: TraceReporterDiagnosticSeverity;\n message: string;\n target?: string;\n}\n\n/** Experimental manifest artifact entry shared by framework reporters. */\nexport interface TraceArtifact {\n kind: TraceArtifactKind;\n path: string;\n format: TraceArtifactFormat;\n redactionProfile: TraceArtifactRedactionProfile;\n title?: string;\n sizeBytes?: number;\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental normalized test result entry shared by framework reporters. */\nexport interface TraceTestResult {\n testId: string;\n name: string;\n file?: string;\n status: TraceTestStatus;\n durationMs?: number;\n tracePath?: string;\n artifacts?: TraceArtifact[];\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental reporter artifact manifest shared by framework reporters. */\nexport interface TraceArtifactManifest {\n schemaVersion: typeof TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION;\n generatedAt: string;\n framework: TraceReporterFramework;\n results: TraceTestResult[];\n artifacts: TraceArtifact[];\n diagnostics: TraceReporterDiagnostic[];\n}\n\n/** Experimental options for deterministic reporter artifact manifest creation. */\nexport interface CreateTraceArtifactManifestOptions {\n framework: TraceReporterFramework;\n generatedAt: string;\n results: TraceTestResult[];\n artifacts?: TraceArtifact[];\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental options for deriving a safe reporter artifact path. */\nexport interface CreateReporterArtifactPathOptions {\n outputDir: string;\n testId: string;\n name: string;\n kind: TraceArtifactKind;\n format: TraceArtifactFormat;\n file?: string;\n}\n\n/** Experimental result from reporter artifact path validation/resolution. */\nexport interface ReporterArtifactPathResult {\n ok: boolean;\n outputDir: string;\n relativePath?: string;\n absolutePath?: string;\n diagnostics: TraceReporterDiagnostic[];\n}\n\nexport interface ValidateReporterArtifactPathOptions {\n outputDir: string;\n relativePath: string;\n}\n\nconst FORMAT_EXTENSIONS: Record<TraceArtifactFormat, string> = {\n json: \"json\",\n jsonl: \"jsonl\",\n md: \"md\",\n html: \"html\",\n};\n\nfunction sortDiagnostics(a: TraceReporterDiagnostic, b: TraceReporterDiagnostic): number {\n return compareStrings(a.target ?? \"\", b.target ?? \"\") ||\n compareStrings(a.code, b.code) ||\n compareStrings(a.severity, b.severity) ||\n compareStrings(a.message, b.message);\n}\n\nfunction sortArtifacts(a: TraceArtifact, b: TraceArtifact): number {\n return compareStrings(a.path, b.path) ||\n compareStrings(a.kind, b.kind) ||\n compareStrings(a.format, b.format) ||\n compareStrings(a.redactionProfile, b.redactionProfile) ||\n compareStrings(a.title ?? \"\", b.title ?? \"\");\n}\n\nfunction sortResults(a: TraceTestResult, b: TraceTestResult): number {\n return compareStrings(a.file ?? \"\", b.file ?? \"\") ||\n compareStrings(a.name, b.name) ||\n compareStrings(a.testId, b.testId);\n}\n\nfunction compareStrings(a: string, b: string): number {\n return a < b ? -1 : a > b ? 1 : 0;\n}\n\nfunction cloneDiagnostic(diagnostic: TraceReporterDiagnostic): TraceReporterDiagnostic {\n return {\n code: diagnostic.code,\n severity: diagnostic.severity,\n message: diagnostic.message,\n ...(diagnostic.target === undefined ? {} : { target: diagnostic.target }),\n };\n}\n\nfunction cloneArtifact(artifact: TraceArtifact): TraceArtifact {\n return {\n kind: artifact.kind,\n path: artifact.path,\n format: artifact.format,\n redactionProfile: artifact.redactionProfile,\n ...(artifact.title === undefined ? {} : { title: artifact.title }),\n ...(artifact.sizeBytes === undefined ? {} : { sizeBytes: artifact.sizeBytes }),\n diagnostics: (artifact.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\nfunction cloneResult(result: TraceTestResult): TraceTestResult {\n return {\n testId: result.testId,\n name: result.name,\n ...(result.file === undefined ? {} : { file: result.file }),\n status: result.status,\n ...(result.durationMs === undefined ? {} : { durationMs: result.durationMs }),\n ...(result.tracePath === undefined ? {} : { tracePath: result.tracePath }),\n artifacts: (result.artifacts ?? []).map(cloneArtifact).sort(sortArtifacts),\n diagnostics: (result.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\nfunction artifactIdentity(artifact: TraceArtifact): string {\n return `${artifact.path}\\0${artifact.kind}\\0${artifact.format}\\0${artifact.redactionProfile}`;\n}\n\nfunction dedupeArtifacts(artifacts: TraceArtifact[]): TraceArtifact[] {\n const seen = new Set<string>();\n const out: TraceArtifact[] = [];\n for (const artifact of artifacts.sort(sortArtifacts)) {\n const key = artifactIdentity(artifact);\n if (seen.has(key)) continue;\n seen.add(key);\n out.push(artifact);\n }\n return out;\n}\n\n/** Experimental helper that creates a deterministic reporter artifact manifest. */\nexport function createTraceArtifactManifest(\n options: CreateTraceArtifactManifestOptions,\n): TraceArtifactManifest {\n const results = options.results.map(cloneResult).sort(sortResults);\n const resultArtifacts = results.flatMap((result) => result.artifacts ?? []);\n const artifacts = dedupeArtifacts([\n ...resultArtifacts,\n ...(options.artifacts ?? []).map(cloneArtifact),\n ]);\n\n return {\n schemaVersion: TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION,\n generatedAt: options.generatedAt,\n framework: options.framework,\n results,\n artifacts,\n diagnostics: (options.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\n/** Experimental helper that creates a safe, deterministic artifact path for a test. */\nexport function createReporterArtifactPath(\n options: CreateReporterArtifactPathOptions,\n): ReporterArtifactPathResult {\n const fileSlug = slugForPathLabel(options.file ?? \"manual\");\n const testSlug = slugForPathLabel(`${options.name}-${options.testId}`);\n const relativePath = path.posix.join(\n \"tests\",\n fileSlug,\n testSlug,\n `${options.kind}.${FORMAT_EXTENSIONS[options.format]}`,\n );\n\n return validateReporterArtifactPath({\n outputDir: options.outputDir,\n relativePath,\n });\n}\n\n/** Experimental helper that validates an artifact path stays inside outputDir. */\nexport function validateReporterArtifactPath(\n options: ValidateReporterArtifactPathOptions,\n): ReporterArtifactPathResult {\n const outputDir = path.resolve(options.outputDir);\n const diagnostics: TraceReporterDiagnostic[] = [];\n const rawPath = options.relativePath;\n\n if (rawPath.length === 0) {\n diagnostics.push({\n code: \"artifact_path_empty\",\n severity: \"error\",\n message: \"Reporter artifact path must not be empty.\",\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n if (rawPath.includes(\"\\0\")) {\n diagnostics.push({\n code: \"invalid_artifact_path\",\n severity: \"error\",\n message: \"Reporter artifact path must not contain null bytes.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n if (path.isAbsolute(rawPath) || path.win32.isAbsolute(rawPath)) {\n diagnostics.push({\n code: \"artifact_path_absolute\",\n severity: \"error\",\n message: \"Reporter artifact path must be relative.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n const normalized = path.posix.normalize(rawPath.replace(/\\\\/g, \"/\"));\n const segments = normalized.split(\"/\");\n if (\n normalized === \".\" ||\n normalized.startsWith(\"../\") ||\n segments.some((segment) => segment === \"..\")\n ) {\n diagnostics.push({\n code: \"artifact_path_escape\",\n severity: \"error\",\n message: \"Reporter artifact path must stay under the output directory.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n const absolutePath = path.resolve(outputDir, normalized);\n const relFromOutput = path.relative(outputDir, absolutePath);\n if (\n relFromOutput.length === 0 ||\n relFromOutput.startsWith(\"..\") ||\n path.isAbsolute(relFromOutput)\n ) {\n diagnostics.push({\n code: \"artifact_path_escape\",\n severity: \"error\",\n message: \"Reporter artifact path resolved outside the output directory.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n return {\n ok: true,\n outputDir,\n relativePath: normalized,\n absolutePath,\n diagnostics,\n };\n}\n\n/** Experimental helper that converts an unknown reporter failure into a diagnostic. */\nexport function createReporterFailureDiagnostic(\n error: unknown,\n target?: string,\n): TraceReporterDiagnostic {\n const message = error instanceof Error\n ? error.message\n : typeof error === \"string\"\n ? error\n : \"Unknown reporter failure.\";\n\n return {\n code: \"reporter_failure\",\n severity: \"error\",\n message,\n ...(target === undefined ? {} : { target }),\n };\n}\n\nfunction slugForPathLabel(value: string): string {\n const base = path.basename(value)\n .replace(/\\.(test|spec)\\.[^.]+$/, \"\")\n .replace(/\\.[^.]+$/, \"\");\n const slug = base\n .toLowerCase()\n .replace(/[^a-z0-9._-]+/g, \"-\")\n .replace(/^[._-]+|[._-]+$/g, \"\")\n .slice(0, 80);\n return slug.length > 0 ? slug : \"artifact\";\n}\n"]}
1
+ {"version":3,"sources":["../src/reporters/index.ts"],"names":["path"],"mappings":"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","file":"reporters.cjs","sourcesContent":["import path from \"node:path\";\n\nexport const TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION = \"0.1\" as const;\n\n/** Experimental reporter framework identifier for local CI artifacts. */\nexport type TraceReporterFramework = \"vitest\" | \"jest\" | \"manual\";\n\n/** Experimental reporter test status normalized across supported test runners. */\nexport type TraceTestStatus = \"passed\" | \"failed\" | \"skipped\" | \"todo\";\n\n/** Experimental reporter artifact kind used in artifact manifests. */\nexport type TraceArtifactKind = \"trace\" | \"report\" | \"eval\" | \"redaction\" | \"summary\" | \"evidence\";\n\n/** Experimental reporter artifact file format used in artifact manifests. */\nexport type TraceArtifactFormat = \"json\" | \"jsonl\" | \"md\" | \"html\";\n\n/** Experimental redaction profile marker recorded with reporter artifacts. */\nexport type TraceArtifactRedactionProfile = \"local\" | \"share\" | \"strict\";\n\n/** Experimental reporter diagnostic severity. */\nexport type TraceReporterDiagnosticSeverity = \"info\" | \"warning\" | \"error\";\n\n/** Experimental reporter diagnostic code for safe, non-throwing reporter helpers. */\nexport type TraceReporterDiagnosticCode =\n | \"invalid_artifact_path\"\n | \"artifact_path_escape\"\n | \"artifact_path_empty\"\n | \"artifact_path_absolute\"\n | \"reporter_failure\";\n\n/** Experimental diagnostic emitted by reporter helpers instead of throwing. */\nexport interface TraceReporterDiagnostic {\n code: TraceReporterDiagnosticCode;\n severity: TraceReporterDiagnosticSeverity;\n message: string;\n target?: string;\n}\n\n/** Experimental manifest artifact entry shared by framework reporters. */\nexport interface TraceArtifact {\n kind: TraceArtifactKind;\n path: string;\n format: TraceArtifactFormat;\n redactionProfile: TraceArtifactRedactionProfile;\n title?: string;\n sizeBytes?: number;\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental normalized test result entry shared by framework reporters. */\nexport interface TraceTestResult {\n testId: string;\n name: string;\n file?: string;\n status: TraceTestStatus;\n durationMs?: number;\n tracePath?: string;\n artifacts?: TraceArtifact[];\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental reporter artifact manifest shared by framework reporters. */\nexport interface TraceArtifactManifest {\n schemaVersion: typeof TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION;\n generatedAt: string;\n framework: TraceReporterFramework;\n results: TraceTestResult[];\n artifacts: TraceArtifact[];\n diagnostics: TraceReporterDiagnostic[];\n}\n\n/** Experimental options for deterministic reporter artifact manifest creation. */\nexport interface CreateTraceArtifactManifestOptions {\n framework: TraceReporterFramework;\n generatedAt: string;\n results: TraceTestResult[];\n artifacts?: TraceArtifact[];\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental options for deriving a safe reporter artifact path. */\nexport interface CreateReporterArtifactPathOptions {\n outputDir: string;\n testId: string;\n name: string;\n kind: TraceArtifactKind;\n format: TraceArtifactFormat;\n file?: string;\n}\n\n/** Experimental result from reporter artifact path validation/resolution. */\nexport interface ReporterArtifactPathResult {\n ok: boolean;\n outputDir: string;\n relativePath?: string;\n absolutePath?: string;\n diagnostics: TraceReporterDiagnostic[];\n}\n\nexport interface ValidateReporterArtifactPathOptions {\n outputDir: string;\n relativePath: string;\n}\n\nconst FORMAT_EXTENSIONS: Record<TraceArtifactFormat, string> = {\n json: \"json\",\n jsonl: \"jsonl\",\n md: \"md\",\n html: \"html\",\n};\n\nfunction sortDiagnostics(a: TraceReporterDiagnostic, b: TraceReporterDiagnostic): number {\n return compareStrings(a.target ?? \"\", b.target ?? \"\") ||\n compareStrings(a.code, b.code) ||\n compareStrings(a.severity, b.severity) ||\n compareStrings(a.message, b.message);\n}\n\nfunction sortArtifacts(a: TraceArtifact, b: TraceArtifact): number {\n return compareStrings(a.path, b.path) ||\n compareStrings(a.kind, b.kind) ||\n compareStrings(a.format, b.format) ||\n compareStrings(a.redactionProfile, b.redactionProfile) ||\n compareStrings(a.title ?? \"\", b.title ?? \"\");\n}\n\nfunction sortResults(a: TraceTestResult, b: TraceTestResult): number {\n return compareStrings(a.file ?? \"\", b.file ?? \"\") ||\n compareStrings(a.name, b.name) ||\n compareStrings(a.testId, b.testId);\n}\n\nfunction compareStrings(a: string, b: string): number {\n return a < b ? -1 : a > b ? 1 : 0;\n}\n\nfunction cloneDiagnostic(diagnostic: TraceReporterDiagnostic): TraceReporterDiagnostic {\n return {\n code: diagnostic.code,\n severity: diagnostic.severity,\n message: diagnostic.message,\n ...(diagnostic.target === undefined ? {} : { target: diagnostic.target }),\n };\n}\n\nfunction cloneArtifact(artifact: TraceArtifact): TraceArtifact {\n return {\n kind: artifact.kind,\n path: artifact.path,\n format: artifact.format,\n redactionProfile: artifact.redactionProfile,\n ...(artifact.title === undefined ? {} : { title: artifact.title }),\n ...(artifact.sizeBytes === undefined ? {} : { sizeBytes: artifact.sizeBytes }),\n diagnostics: (artifact.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\nfunction cloneResult(result: TraceTestResult): TraceTestResult {\n return {\n testId: result.testId,\n name: result.name,\n ...(result.file === undefined ? {} : { file: result.file }),\n status: result.status,\n ...(result.durationMs === undefined ? {} : { durationMs: result.durationMs }),\n ...(result.tracePath === undefined ? {} : { tracePath: result.tracePath }),\n artifacts: (result.artifacts ?? []).map(cloneArtifact).sort(sortArtifacts),\n diagnostics: (result.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\nfunction artifactIdentity(artifact: TraceArtifact): string {\n return `${artifact.path}\\0${artifact.kind}\\0${artifact.format}\\0${artifact.redactionProfile}`;\n}\n\nfunction dedupeArtifacts(artifacts: TraceArtifact[]): TraceArtifact[] {\n const seen = new Set<string>();\n const out: TraceArtifact[] = [];\n for (const artifact of artifacts.sort(sortArtifacts)) {\n const key = artifactIdentity(artifact);\n if (seen.has(key)) continue;\n seen.add(key);\n out.push(artifact);\n }\n return out;\n}\n\n/** Experimental helper that creates a deterministic reporter artifact manifest. */\nexport function createTraceArtifactManifest(\n options: CreateTraceArtifactManifestOptions,\n): TraceArtifactManifest {\n const results = options.results.map(cloneResult).sort(sortResults);\n const resultArtifacts = results.flatMap((result) => result.artifacts ?? []);\n const artifacts = dedupeArtifacts([\n ...resultArtifacts,\n ...(options.artifacts ?? []).map(cloneArtifact),\n ]);\n\n return {\n schemaVersion: TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION,\n generatedAt: options.generatedAt,\n framework: options.framework,\n results,\n artifacts,\n diagnostics: (options.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\n/** Experimental helper that creates a safe, deterministic artifact path for a test. */\nexport function createReporterArtifactPath(\n options: CreateReporterArtifactPathOptions,\n): ReporterArtifactPathResult {\n const fileSlug = slugForPathLabel(options.file ?? \"manual\");\n const testSlug = slugForPathLabel(`${options.name}-${options.testId}`);\n const relativePath = path.posix.join(\n \"tests\",\n fileSlug,\n testSlug,\n `${options.kind}.${FORMAT_EXTENSIONS[options.format]}`,\n );\n\n return validateReporterArtifactPath({\n outputDir: options.outputDir,\n relativePath,\n });\n}\n\n/** Experimental helper that validates an artifact path stays inside outputDir. */\nexport function validateReporterArtifactPath(\n options: ValidateReporterArtifactPathOptions,\n): ReporterArtifactPathResult {\n const outputDir = path.resolve(options.outputDir);\n const diagnostics: TraceReporterDiagnostic[] = [];\n const rawPath = options.relativePath;\n\n if (rawPath.length === 0) {\n diagnostics.push({\n code: \"artifact_path_empty\",\n severity: \"error\",\n message: \"Reporter artifact path must not be empty.\",\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n if (rawPath.includes(\"\\0\")) {\n diagnostics.push({\n code: \"invalid_artifact_path\",\n severity: \"error\",\n message: \"Reporter artifact path must not contain null bytes.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n if (path.isAbsolute(rawPath) || path.win32.isAbsolute(rawPath)) {\n diagnostics.push({\n code: \"artifact_path_absolute\",\n severity: \"error\",\n message: \"Reporter artifact path must be relative.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n const normalized = path.posix.normalize(rawPath.replace(/\\\\/g, \"/\"));\n const segments = normalized.split(\"/\");\n if (\n normalized === \".\" ||\n normalized.startsWith(\"../\") ||\n segments.some((segment) => segment === \"..\")\n ) {\n diagnostics.push({\n code: \"artifact_path_escape\",\n severity: \"error\",\n message: \"Reporter artifact path must stay under the output directory.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n const absolutePath = path.resolve(outputDir, normalized);\n const relFromOutput = path.relative(outputDir, absolutePath);\n if (\n relFromOutput.length === 0 ||\n relFromOutput.startsWith(\"..\") ||\n path.isAbsolute(relFromOutput)\n ) {\n diagnostics.push({\n code: \"artifact_path_escape\",\n severity: \"error\",\n message: \"Reporter artifact path resolved outside the output directory.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n return {\n ok: true,\n outputDir,\n relativePath: normalized,\n absolutePath,\n diagnostics,\n };\n}\n\n/** Experimental helper that converts an unknown reporter failure into a diagnostic. */\nexport function createReporterFailureDiagnostic(\n error: unknown,\n target?: string,\n): TraceReporterDiagnostic {\n const message = error instanceof Error\n ? error.message\n : typeof error === \"string\"\n ? error\n : \"Unknown reporter failure.\";\n\n return {\n code: \"reporter_failure\",\n severity: \"error\",\n message,\n ...(target === undefined ? {} : { target }),\n };\n}\n\nfunction slugForPathLabel(value: string): string {\n const base = path.basename(value)\n .replace(/\\.(test|spec)\\.[^.]+$/, \"\")\n .replace(/\\.[^.]+$/, \"\");\n const slug = base\n .toLowerCase()\n .replace(/[^a-z0-9._-]+/g, \"-\")\n .replace(/^[._-]+|[._-]+$/g, \"\")\n .slice(0, 80);\n return slug.length > 0 ? slug : \"artifact\";\n}\n\n/**\n * Standard Evidence v2 filenames for CI failure packages (same shape as `bundle`).\n * Success remains quiet by default — callers should emit these only on failure.\n */\nexport const EVIDENCE_CI_ARTIFACT_FILES = [\n \"evidence.html\",\n \"evidence.json\",\n \"check-results.json\",\n \"trace.jsonl\",\n] as const;\n\nexport type EvidenceCiArtifactFile = (typeof EVIDENCE_CI_ARTIFACT_FILES)[number];\n\n/**\n * Experimental helper: TraceArtifact entries for a standard Evidence v2 CI package.\n */\nexport function createEvidenceCiArtifacts(options: {\n redactionProfile?: TraceArtifactRedactionProfile;\n /** Optional subdirectory under the test artifact folder (POSIX). */\n relativeDir?: string;\n}): TraceArtifact[] {\n const profile = options.redactionProfile ?? \"share\";\n const prefix =\n options.relativeDir !== undefined && options.relativeDir.trim() !== \"\"\n ? options.relativeDir.replace(/\\\\/g, \"/\").replace(/^\\/+|\\/+$/g, \"\")\n : \"\";\n const join = (name: string): string => (prefix === \"\" ? name : path.posix.join(prefix, name));\n\n const formatFor = (name: EvidenceCiArtifactFile): TraceArtifactFormat => {\n if (name.endsWith(\".html\")) return \"html\";\n if (name.endsWith(\".jsonl\")) return \"jsonl\";\n return \"json\";\n };\n\n return EVIDENCE_CI_ARTIFACT_FILES.map((name) => ({\n kind: \"evidence\" as const,\n path: join(name),\n format: formatFor(name),\n redactionProfile: profile,\n title: `Evidence v2 ${name}`,\n }));\n}\n"]}
@@ -4,7 +4,7 @@ type TraceReporterFramework = "vitest" | "jest" | "manual";
4
4
  /** Experimental reporter test status normalized across supported test runners. */
5
5
  type TraceTestStatus = "passed" | "failed" | "skipped" | "todo";
6
6
  /** Experimental reporter artifact kind used in artifact manifests. */
7
- type TraceArtifactKind = "trace" | "report" | "eval" | "redaction" | "summary";
7
+ type TraceArtifactKind = "trace" | "report" | "eval" | "redaction" | "summary" | "evidence";
8
8
  /** Experimental reporter artifact file format used in artifact manifests. */
9
9
  type TraceArtifactFormat = "json" | "jsonl" | "md" | "html";
10
10
  /** Experimental redaction profile marker recorded with reporter artifacts. */
@@ -87,5 +87,19 @@ declare function createReporterArtifactPath(options: CreateReporterArtifactPathO
87
87
  declare function validateReporterArtifactPath(options: ValidateReporterArtifactPathOptions): ReporterArtifactPathResult;
88
88
  /** Experimental helper that converts an unknown reporter failure into a diagnostic. */
89
89
  declare function createReporterFailureDiagnostic(error: unknown, target?: string): TraceReporterDiagnostic;
90
+ /**
91
+ * Standard Evidence v2 filenames for CI failure packages (same shape as `bundle`).
92
+ * Success remains quiet by default — callers should emit these only on failure.
93
+ */
94
+ declare const EVIDENCE_CI_ARTIFACT_FILES: readonly ["evidence.html", "evidence.json", "check-results.json", "trace.jsonl"];
95
+ type EvidenceCiArtifactFile = (typeof EVIDENCE_CI_ARTIFACT_FILES)[number];
96
+ /**
97
+ * Experimental helper: TraceArtifact entries for a standard Evidence v2 CI package.
98
+ */
99
+ declare function createEvidenceCiArtifacts(options: {
100
+ redactionProfile?: TraceArtifactRedactionProfile;
101
+ /** Optional subdirectory under the test artifact folder (POSIX). */
102
+ relativeDir?: string;
103
+ }): TraceArtifact[];
90
104
 
91
- export { type CreateReporterArtifactPathOptions, type CreateTraceArtifactManifestOptions, type ReporterArtifactPathResult, TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION, type TraceArtifact, type TraceArtifactFormat, type TraceArtifactKind, type TraceArtifactManifest, type TraceArtifactRedactionProfile, type TraceReporterDiagnostic, type TraceReporterDiagnosticCode, type TraceReporterDiagnosticSeverity, type TraceReporterFramework, type TraceTestResult, type TraceTestStatus, type ValidateReporterArtifactPathOptions, createReporterArtifactPath, createReporterFailureDiagnostic, createTraceArtifactManifest, validateReporterArtifactPath };
105
+ export { type CreateReporterArtifactPathOptions, type CreateTraceArtifactManifestOptions, EVIDENCE_CI_ARTIFACT_FILES, type EvidenceCiArtifactFile, type ReporterArtifactPathResult, TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION, type TraceArtifact, type TraceArtifactFormat, type TraceArtifactKind, type TraceArtifactManifest, type TraceArtifactRedactionProfile, type TraceReporterDiagnostic, type TraceReporterDiagnosticCode, type TraceReporterDiagnosticSeverity, type TraceReporterFramework, type TraceTestResult, type TraceTestStatus, type ValidateReporterArtifactPathOptions, createEvidenceCiArtifacts, createReporterArtifactPath, createReporterFailureDiagnostic, createTraceArtifactManifest, validateReporterArtifactPath };
@@ -4,7 +4,7 @@ type TraceReporterFramework = "vitest" | "jest" | "manual";
4
4
  /** Experimental reporter test status normalized across supported test runners. */
5
5
  type TraceTestStatus = "passed" | "failed" | "skipped" | "todo";
6
6
  /** Experimental reporter artifact kind used in artifact manifests. */
7
- type TraceArtifactKind = "trace" | "report" | "eval" | "redaction" | "summary";
7
+ type TraceArtifactKind = "trace" | "report" | "eval" | "redaction" | "summary" | "evidence";
8
8
  /** Experimental reporter artifact file format used in artifact manifests. */
9
9
  type TraceArtifactFormat = "json" | "jsonl" | "md" | "html";
10
10
  /** Experimental redaction profile marker recorded with reporter artifacts. */
@@ -87,5 +87,19 @@ declare function createReporterArtifactPath(options: CreateReporterArtifactPathO
87
87
  declare function validateReporterArtifactPath(options: ValidateReporterArtifactPathOptions): ReporterArtifactPathResult;
88
88
  /** Experimental helper that converts an unknown reporter failure into a diagnostic. */
89
89
  declare function createReporterFailureDiagnostic(error: unknown, target?: string): TraceReporterDiagnostic;
90
+ /**
91
+ * Standard Evidence v2 filenames for CI failure packages (same shape as `bundle`).
92
+ * Success remains quiet by default — callers should emit these only on failure.
93
+ */
94
+ declare const EVIDENCE_CI_ARTIFACT_FILES: readonly ["evidence.html", "evidence.json", "check-results.json", "trace.jsonl"];
95
+ type EvidenceCiArtifactFile = (typeof EVIDENCE_CI_ARTIFACT_FILES)[number];
96
+ /**
97
+ * Experimental helper: TraceArtifact entries for a standard Evidence v2 CI package.
98
+ */
99
+ declare function createEvidenceCiArtifacts(options: {
100
+ redactionProfile?: TraceArtifactRedactionProfile;
101
+ /** Optional subdirectory under the test artifact folder (POSIX). */
102
+ relativeDir?: string;
103
+ }): TraceArtifact[];
90
104
 
91
- export { type CreateReporterArtifactPathOptions, type CreateTraceArtifactManifestOptions, type ReporterArtifactPathResult, TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION, type TraceArtifact, type TraceArtifactFormat, type TraceArtifactKind, type TraceArtifactManifest, type TraceArtifactRedactionProfile, type TraceReporterDiagnostic, type TraceReporterDiagnosticCode, type TraceReporterDiagnosticSeverity, type TraceReporterFramework, type TraceTestResult, type TraceTestStatus, type ValidateReporterArtifactPathOptions, createReporterArtifactPath, createReporterFailureDiagnostic, createTraceArtifactManifest, validateReporterArtifactPath };
105
+ export { type CreateReporterArtifactPathOptions, type CreateTraceArtifactManifestOptions, EVIDENCE_CI_ARTIFACT_FILES, type EvidenceCiArtifactFile, type ReporterArtifactPathResult, TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION, type TraceArtifact, type TraceArtifactFormat, type TraceArtifactKind, type TraceArtifactManifest, type TraceArtifactRedactionProfile, type TraceReporterDiagnostic, type TraceReporterDiagnosticCode, type TraceReporterDiagnosticSeverity, type TraceReporterFramework, type TraceTestResult, type TraceTestStatus, type ValidateReporterArtifactPathOptions, createEvidenceCiArtifacts, createReporterArtifactPath, createReporterFailureDiagnostic, createTraceArtifactManifest, validateReporterArtifactPath };
@@ -169,7 +169,30 @@ function slugForPathLabel(value) {
169
169
  const slug = base.toLowerCase().replace(/[^a-z0-9._-]+/g, "-").replace(/^[._-]+|[._-]+$/g, "").slice(0, 80);
170
170
  return slug.length > 0 ? slug : "artifact";
171
171
  }
172
+ var EVIDENCE_CI_ARTIFACT_FILES = [
173
+ "evidence.html",
174
+ "evidence.json",
175
+ "check-results.json",
176
+ "trace.jsonl"
177
+ ];
178
+ function createEvidenceCiArtifacts(options) {
179
+ const profile = options.redactionProfile ?? "share";
180
+ const prefix = options.relativeDir !== void 0 && options.relativeDir.trim() !== "" ? options.relativeDir.replace(/\\/g, "/").replace(/^\/+|\/+$/g, "") : "";
181
+ const join = (name) => prefix === "" ? name : path.posix.join(prefix, name);
182
+ const formatFor = (name) => {
183
+ if (name.endsWith(".html")) return "html";
184
+ if (name.endsWith(".jsonl")) return "jsonl";
185
+ return "json";
186
+ };
187
+ return EVIDENCE_CI_ARTIFACT_FILES.map((name) => ({
188
+ kind: "evidence",
189
+ path: join(name),
190
+ format: formatFor(name),
191
+ redactionProfile: profile,
192
+ title: `Evidence v2 ${name}`
193
+ }));
194
+ }
172
195
 
173
- export { TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION, createReporterArtifactPath, createReporterFailureDiagnostic, createTraceArtifactManifest, validateReporterArtifactPath };
196
+ export { EVIDENCE_CI_ARTIFACT_FILES, TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION, createEvidenceCiArtifacts, createReporterArtifactPath, createReporterFailureDiagnostic, createTraceArtifactManifest, validateReporterArtifactPath };
174
197
  //# sourceMappingURL=reporters.mjs.map
175
198
  //# sourceMappingURL=reporters.mjs.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/reporters/index.ts"],"names":[],"mappings":"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","file":"reporters.mjs","sourcesContent":["import path from \"node:path\";\n\nexport const TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION = \"0.1\" as const;\n\n/** Experimental reporter framework identifier for local CI artifacts. */\nexport type TraceReporterFramework = \"vitest\" | \"jest\" | \"manual\";\n\n/** Experimental reporter test status normalized across supported test runners. */\nexport type TraceTestStatus = \"passed\" | \"failed\" | \"skipped\" | \"todo\";\n\n/** Experimental reporter artifact kind used in artifact manifests. */\nexport type TraceArtifactKind = \"trace\" | \"report\" | \"eval\" | \"redaction\" | \"summary\";\n\n/** Experimental reporter artifact file format used in artifact manifests. */\nexport type TraceArtifactFormat = \"json\" | \"jsonl\" | \"md\" | \"html\";\n\n/** Experimental redaction profile marker recorded with reporter artifacts. */\nexport type TraceArtifactRedactionProfile = \"local\" | \"share\" | \"strict\";\n\n/** Experimental reporter diagnostic severity. */\nexport type TraceReporterDiagnosticSeverity = \"info\" | \"warning\" | \"error\";\n\n/** Experimental reporter diagnostic code for safe, non-throwing reporter helpers. */\nexport type TraceReporterDiagnosticCode =\n | \"invalid_artifact_path\"\n | \"artifact_path_escape\"\n | \"artifact_path_empty\"\n | \"artifact_path_absolute\"\n | \"reporter_failure\";\n\n/** Experimental diagnostic emitted by reporter helpers instead of throwing. */\nexport interface TraceReporterDiagnostic {\n code: TraceReporterDiagnosticCode;\n severity: TraceReporterDiagnosticSeverity;\n message: string;\n target?: string;\n}\n\n/** Experimental manifest artifact entry shared by framework reporters. */\nexport interface TraceArtifact {\n kind: TraceArtifactKind;\n path: string;\n format: TraceArtifactFormat;\n redactionProfile: TraceArtifactRedactionProfile;\n title?: string;\n sizeBytes?: number;\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental normalized test result entry shared by framework reporters. */\nexport interface TraceTestResult {\n testId: string;\n name: string;\n file?: string;\n status: TraceTestStatus;\n durationMs?: number;\n tracePath?: string;\n artifacts?: TraceArtifact[];\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental reporter artifact manifest shared by framework reporters. */\nexport interface TraceArtifactManifest {\n schemaVersion: typeof TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION;\n generatedAt: string;\n framework: TraceReporterFramework;\n results: TraceTestResult[];\n artifacts: TraceArtifact[];\n diagnostics: TraceReporterDiagnostic[];\n}\n\n/** Experimental options for deterministic reporter artifact manifest creation. */\nexport interface CreateTraceArtifactManifestOptions {\n framework: TraceReporterFramework;\n generatedAt: string;\n results: TraceTestResult[];\n artifacts?: TraceArtifact[];\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental options for deriving a safe reporter artifact path. */\nexport interface CreateReporterArtifactPathOptions {\n outputDir: string;\n testId: string;\n name: string;\n kind: TraceArtifactKind;\n format: TraceArtifactFormat;\n file?: string;\n}\n\n/** Experimental result from reporter artifact path validation/resolution. */\nexport interface ReporterArtifactPathResult {\n ok: boolean;\n outputDir: string;\n relativePath?: string;\n absolutePath?: string;\n diagnostics: TraceReporterDiagnostic[];\n}\n\nexport interface ValidateReporterArtifactPathOptions {\n outputDir: string;\n relativePath: string;\n}\n\nconst FORMAT_EXTENSIONS: Record<TraceArtifactFormat, string> = {\n json: \"json\",\n jsonl: \"jsonl\",\n md: \"md\",\n html: \"html\",\n};\n\nfunction sortDiagnostics(a: TraceReporterDiagnostic, b: TraceReporterDiagnostic): number {\n return compareStrings(a.target ?? \"\", b.target ?? \"\") ||\n compareStrings(a.code, b.code) ||\n compareStrings(a.severity, b.severity) ||\n compareStrings(a.message, b.message);\n}\n\nfunction sortArtifacts(a: TraceArtifact, b: TraceArtifact): number {\n return compareStrings(a.path, b.path) ||\n compareStrings(a.kind, b.kind) ||\n compareStrings(a.format, b.format) ||\n compareStrings(a.redactionProfile, b.redactionProfile) ||\n compareStrings(a.title ?? \"\", b.title ?? \"\");\n}\n\nfunction sortResults(a: TraceTestResult, b: TraceTestResult): number {\n return compareStrings(a.file ?? \"\", b.file ?? \"\") ||\n compareStrings(a.name, b.name) ||\n compareStrings(a.testId, b.testId);\n}\n\nfunction compareStrings(a: string, b: string): number {\n return a < b ? -1 : a > b ? 1 : 0;\n}\n\nfunction cloneDiagnostic(diagnostic: TraceReporterDiagnostic): TraceReporterDiagnostic {\n return {\n code: diagnostic.code,\n severity: diagnostic.severity,\n message: diagnostic.message,\n ...(diagnostic.target === undefined ? {} : { target: diagnostic.target }),\n };\n}\n\nfunction cloneArtifact(artifact: TraceArtifact): TraceArtifact {\n return {\n kind: artifact.kind,\n path: artifact.path,\n format: artifact.format,\n redactionProfile: artifact.redactionProfile,\n ...(artifact.title === undefined ? {} : { title: artifact.title }),\n ...(artifact.sizeBytes === undefined ? {} : { sizeBytes: artifact.sizeBytes }),\n diagnostics: (artifact.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\nfunction cloneResult(result: TraceTestResult): TraceTestResult {\n return {\n testId: result.testId,\n name: result.name,\n ...(result.file === undefined ? {} : { file: result.file }),\n status: result.status,\n ...(result.durationMs === undefined ? {} : { durationMs: result.durationMs }),\n ...(result.tracePath === undefined ? {} : { tracePath: result.tracePath }),\n artifacts: (result.artifacts ?? []).map(cloneArtifact).sort(sortArtifacts),\n diagnostics: (result.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\nfunction artifactIdentity(artifact: TraceArtifact): string {\n return `${artifact.path}\\0${artifact.kind}\\0${artifact.format}\\0${artifact.redactionProfile}`;\n}\n\nfunction dedupeArtifacts(artifacts: TraceArtifact[]): TraceArtifact[] {\n const seen = new Set<string>();\n const out: TraceArtifact[] = [];\n for (const artifact of artifacts.sort(sortArtifacts)) {\n const key = artifactIdentity(artifact);\n if (seen.has(key)) continue;\n seen.add(key);\n out.push(artifact);\n }\n return out;\n}\n\n/** Experimental helper that creates a deterministic reporter artifact manifest. */\nexport function createTraceArtifactManifest(\n options: CreateTraceArtifactManifestOptions,\n): TraceArtifactManifest {\n const results = options.results.map(cloneResult).sort(sortResults);\n const resultArtifacts = results.flatMap((result) => result.artifacts ?? []);\n const artifacts = dedupeArtifacts([\n ...resultArtifacts,\n ...(options.artifacts ?? []).map(cloneArtifact),\n ]);\n\n return {\n schemaVersion: TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION,\n generatedAt: options.generatedAt,\n framework: options.framework,\n results,\n artifacts,\n diagnostics: (options.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\n/** Experimental helper that creates a safe, deterministic artifact path for a test. */\nexport function createReporterArtifactPath(\n options: CreateReporterArtifactPathOptions,\n): ReporterArtifactPathResult {\n const fileSlug = slugForPathLabel(options.file ?? \"manual\");\n const testSlug = slugForPathLabel(`${options.name}-${options.testId}`);\n const relativePath = path.posix.join(\n \"tests\",\n fileSlug,\n testSlug,\n `${options.kind}.${FORMAT_EXTENSIONS[options.format]}`,\n );\n\n return validateReporterArtifactPath({\n outputDir: options.outputDir,\n relativePath,\n });\n}\n\n/** Experimental helper that validates an artifact path stays inside outputDir. */\nexport function validateReporterArtifactPath(\n options: ValidateReporterArtifactPathOptions,\n): ReporterArtifactPathResult {\n const outputDir = path.resolve(options.outputDir);\n const diagnostics: TraceReporterDiagnostic[] = [];\n const rawPath = options.relativePath;\n\n if (rawPath.length === 0) {\n diagnostics.push({\n code: \"artifact_path_empty\",\n severity: \"error\",\n message: \"Reporter artifact path must not be empty.\",\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n if (rawPath.includes(\"\\0\")) {\n diagnostics.push({\n code: \"invalid_artifact_path\",\n severity: \"error\",\n message: \"Reporter artifact path must not contain null bytes.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n if (path.isAbsolute(rawPath) || path.win32.isAbsolute(rawPath)) {\n diagnostics.push({\n code: \"artifact_path_absolute\",\n severity: \"error\",\n message: \"Reporter artifact path must be relative.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n const normalized = path.posix.normalize(rawPath.replace(/\\\\/g, \"/\"));\n const segments = normalized.split(\"/\");\n if (\n normalized === \".\" ||\n normalized.startsWith(\"../\") ||\n segments.some((segment) => segment === \"..\")\n ) {\n diagnostics.push({\n code: \"artifact_path_escape\",\n severity: \"error\",\n message: \"Reporter artifact path must stay under the output directory.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n const absolutePath = path.resolve(outputDir, normalized);\n const relFromOutput = path.relative(outputDir, absolutePath);\n if (\n relFromOutput.length === 0 ||\n relFromOutput.startsWith(\"..\") ||\n path.isAbsolute(relFromOutput)\n ) {\n diagnostics.push({\n code: \"artifact_path_escape\",\n severity: \"error\",\n message: \"Reporter artifact path resolved outside the output directory.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n return {\n ok: true,\n outputDir,\n relativePath: normalized,\n absolutePath,\n diagnostics,\n };\n}\n\n/** Experimental helper that converts an unknown reporter failure into a diagnostic. */\nexport function createReporterFailureDiagnostic(\n error: unknown,\n target?: string,\n): TraceReporterDiagnostic {\n const message = error instanceof Error\n ? error.message\n : typeof error === \"string\"\n ? error\n : \"Unknown reporter failure.\";\n\n return {\n code: \"reporter_failure\",\n severity: \"error\",\n message,\n ...(target === undefined ? {} : { target }),\n };\n}\n\nfunction slugForPathLabel(value: string): string {\n const base = path.basename(value)\n .replace(/\\.(test|spec)\\.[^.]+$/, \"\")\n .replace(/\\.[^.]+$/, \"\");\n const slug = base\n .toLowerCase()\n .replace(/[^a-z0-9._-]+/g, \"-\")\n .replace(/^[._-]+|[._-]+$/g, \"\")\n .slice(0, 80);\n return slug.length > 0 ? slug : \"artifact\";\n}\n"]}
1
+ {"version":3,"sources":["../src/reporters/index.ts"],"names":[],"mappings":"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","file":"reporters.mjs","sourcesContent":["import path from \"node:path\";\n\nexport const TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION = \"0.1\" as const;\n\n/** Experimental reporter framework identifier for local CI artifacts. */\nexport type TraceReporterFramework = \"vitest\" | \"jest\" | \"manual\";\n\n/** Experimental reporter test status normalized across supported test runners. */\nexport type TraceTestStatus = \"passed\" | \"failed\" | \"skipped\" | \"todo\";\n\n/** Experimental reporter artifact kind used in artifact manifests. */\nexport type TraceArtifactKind = \"trace\" | \"report\" | \"eval\" | \"redaction\" | \"summary\" | \"evidence\";\n\n/** Experimental reporter artifact file format used in artifact manifests. */\nexport type TraceArtifactFormat = \"json\" | \"jsonl\" | \"md\" | \"html\";\n\n/** Experimental redaction profile marker recorded with reporter artifacts. */\nexport type TraceArtifactRedactionProfile = \"local\" | \"share\" | \"strict\";\n\n/** Experimental reporter diagnostic severity. */\nexport type TraceReporterDiagnosticSeverity = \"info\" | \"warning\" | \"error\";\n\n/** Experimental reporter diagnostic code for safe, non-throwing reporter helpers. */\nexport type TraceReporterDiagnosticCode =\n | \"invalid_artifact_path\"\n | \"artifact_path_escape\"\n | \"artifact_path_empty\"\n | \"artifact_path_absolute\"\n | \"reporter_failure\";\n\n/** Experimental diagnostic emitted by reporter helpers instead of throwing. */\nexport interface TraceReporterDiagnostic {\n code: TraceReporterDiagnosticCode;\n severity: TraceReporterDiagnosticSeverity;\n message: string;\n target?: string;\n}\n\n/** Experimental manifest artifact entry shared by framework reporters. */\nexport interface TraceArtifact {\n kind: TraceArtifactKind;\n path: string;\n format: TraceArtifactFormat;\n redactionProfile: TraceArtifactRedactionProfile;\n title?: string;\n sizeBytes?: number;\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental normalized test result entry shared by framework reporters. */\nexport interface TraceTestResult {\n testId: string;\n name: string;\n file?: string;\n status: TraceTestStatus;\n durationMs?: number;\n tracePath?: string;\n artifacts?: TraceArtifact[];\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental reporter artifact manifest shared by framework reporters. */\nexport interface TraceArtifactManifest {\n schemaVersion: typeof TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION;\n generatedAt: string;\n framework: TraceReporterFramework;\n results: TraceTestResult[];\n artifacts: TraceArtifact[];\n diagnostics: TraceReporterDiagnostic[];\n}\n\n/** Experimental options for deterministic reporter artifact manifest creation. */\nexport interface CreateTraceArtifactManifestOptions {\n framework: TraceReporterFramework;\n generatedAt: string;\n results: TraceTestResult[];\n artifacts?: TraceArtifact[];\n diagnostics?: TraceReporterDiagnostic[];\n}\n\n/** Experimental options for deriving a safe reporter artifact path. */\nexport interface CreateReporterArtifactPathOptions {\n outputDir: string;\n testId: string;\n name: string;\n kind: TraceArtifactKind;\n format: TraceArtifactFormat;\n file?: string;\n}\n\n/** Experimental result from reporter artifact path validation/resolution. */\nexport interface ReporterArtifactPathResult {\n ok: boolean;\n outputDir: string;\n relativePath?: string;\n absolutePath?: string;\n diagnostics: TraceReporterDiagnostic[];\n}\n\nexport interface ValidateReporterArtifactPathOptions {\n outputDir: string;\n relativePath: string;\n}\n\nconst FORMAT_EXTENSIONS: Record<TraceArtifactFormat, string> = {\n json: \"json\",\n jsonl: \"jsonl\",\n md: \"md\",\n html: \"html\",\n};\n\nfunction sortDiagnostics(a: TraceReporterDiagnostic, b: TraceReporterDiagnostic): number {\n return compareStrings(a.target ?? \"\", b.target ?? \"\") ||\n compareStrings(a.code, b.code) ||\n compareStrings(a.severity, b.severity) ||\n compareStrings(a.message, b.message);\n}\n\nfunction sortArtifacts(a: TraceArtifact, b: TraceArtifact): number {\n return compareStrings(a.path, b.path) ||\n compareStrings(a.kind, b.kind) ||\n compareStrings(a.format, b.format) ||\n compareStrings(a.redactionProfile, b.redactionProfile) ||\n compareStrings(a.title ?? \"\", b.title ?? \"\");\n}\n\nfunction sortResults(a: TraceTestResult, b: TraceTestResult): number {\n return compareStrings(a.file ?? \"\", b.file ?? \"\") ||\n compareStrings(a.name, b.name) ||\n compareStrings(a.testId, b.testId);\n}\n\nfunction compareStrings(a: string, b: string): number {\n return a < b ? -1 : a > b ? 1 : 0;\n}\n\nfunction cloneDiagnostic(diagnostic: TraceReporterDiagnostic): TraceReporterDiagnostic {\n return {\n code: diagnostic.code,\n severity: diagnostic.severity,\n message: diagnostic.message,\n ...(diagnostic.target === undefined ? {} : { target: diagnostic.target }),\n };\n}\n\nfunction cloneArtifact(artifact: TraceArtifact): TraceArtifact {\n return {\n kind: artifact.kind,\n path: artifact.path,\n format: artifact.format,\n redactionProfile: artifact.redactionProfile,\n ...(artifact.title === undefined ? {} : { title: artifact.title }),\n ...(artifact.sizeBytes === undefined ? {} : { sizeBytes: artifact.sizeBytes }),\n diagnostics: (artifact.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\nfunction cloneResult(result: TraceTestResult): TraceTestResult {\n return {\n testId: result.testId,\n name: result.name,\n ...(result.file === undefined ? {} : { file: result.file }),\n status: result.status,\n ...(result.durationMs === undefined ? {} : { durationMs: result.durationMs }),\n ...(result.tracePath === undefined ? {} : { tracePath: result.tracePath }),\n artifacts: (result.artifacts ?? []).map(cloneArtifact).sort(sortArtifacts),\n diagnostics: (result.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\nfunction artifactIdentity(artifact: TraceArtifact): string {\n return `${artifact.path}\\0${artifact.kind}\\0${artifact.format}\\0${artifact.redactionProfile}`;\n}\n\nfunction dedupeArtifacts(artifacts: TraceArtifact[]): TraceArtifact[] {\n const seen = new Set<string>();\n const out: TraceArtifact[] = [];\n for (const artifact of artifacts.sort(sortArtifacts)) {\n const key = artifactIdentity(artifact);\n if (seen.has(key)) continue;\n seen.add(key);\n out.push(artifact);\n }\n return out;\n}\n\n/** Experimental helper that creates a deterministic reporter artifact manifest. */\nexport function createTraceArtifactManifest(\n options: CreateTraceArtifactManifestOptions,\n): TraceArtifactManifest {\n const results = options.results.map(cloneResult).sort(sortResults);\n const resultArtifacts = results.flatMap((result) => result.artifacts ?? []);\n const artifacts = dedupeArtifacts([\n ...resultArtifacts,\n ...(options.artifacts ?? []).map(cloneArtifact),\n ]);\n\n return {\n schemaVersion: TRACE_ARTIFACT_MANIFEST_SCHEMA_VERSION,\n generatedAt: options.generatedAt,\n framework: options.framework,\n results,\n artifacts,\n diagnostics: (options.diagnostics ?? []).map(cloneDiagnostic).sort(sortDiagnostics),\n };\n}\n\n/** Experimental helper that creates a safe, deterministic artifact path for a test. */\nexport function createReporterArtifactPath(\n options: CreateReporterArtifactPathOptions,\n): ReporterArtifactPathResult {\n const fileSlug = slugForPathLabel(options.file ?? \"manual\");\n const testSlug = slugForPathLabel(`${options.name}-${options.testId}`);\n const relativePath = path.posix.join(\n \"tests\",\n fileSlug,\n testSlug,\n `${options.kind}.${FORMAT_EXTENSIONS[options.format]}`,\n );\n\n return validateReporterArtifactPath({\n outputDir: options.outputDir,\n relativePath,\n });\n}\n\n/** Experimental helper that validates an artifact path stays inside outputDir. */\nexport function validateReporterArtifactPath(\n options: ValidateReporterArtifactPathOptions,\n): ReporterArtifactPathResult {\n const outputDir = path.resolve(options.outputDir);\n const diagnostics: TraceReporterDiagnostic[] = [];\n const rawPath = options.relativePath;\n\n if (rawPath.length === 0) {\n diagnostics.push({\n code: \"artifact_path_empty\",\n severity: \"error\",\n message: \"Reporter artifact path must not be empty.\",\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n if (rawPath.includes(\"\\0\")) {\n diagnostics.push({\n code: \"invalid_artifact_path\",\n severity: \"error\",\n message: \"Reporter artifact path must not contain null bytes.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n if (path.isAbsolute(rawPath) || path.win32.isAbsolute(rawPath)) {\n diagnostics.push({\n code: \"artifact_path_absolute\",\n severity: \"error\",\n message: \"Reporter artifact path must be relative.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n const normalized = path.posix.normalize(rawPath.replace(/\\\\/g, \"/\"));\n const segments = normalized.split(\"/\");\n if (\n normalized === \".\" ||\n normalized.startsWith(\"../\") ||\n segments.some((segment) => segment === \"..\")\n ) {\n diagnostics.push({\n code: \"artifact_path_escape\",\n severity: \"error\",\n message: \"Reporter artifact path must stay under the output directory.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n const absolutePath = path.resolve(outputDir, normalized);\n const relFromOutput = path.relative(outputDir, absolutePath);\n if (\n relFromOutput.length === 0 ||\n relFromOutput.startsWith(\"..\") ||\n path.isAbsolute(relFromOutput)\n ) {\n diagnostics.push({\n code: \"artifact_path_escape\",\n severity: \"error\",\n message: \"Reporter artifact path resolved outside the output directory.\",\n target: rawPath,\n });\n return { ok: false, outputDir, diagnostics };\n }\n\n return {\n ok: true,\n outputDir,\n relativePath: normalized,\n absolutePath,\n diagnostics,\n };\n}\n\n/** Experimental helper that converts an unknown reporter failure into a diagnostic. */\nexport function createReporterFailureDiagnostic(\n error: unknown,\n target?: string,\n): TraceReporterDiagnostic {\n const message = error instanceof Error\n ? error.message\n : typeof error === \"string\"\n ? error\n : \"Unknown reporter failure.\";\n\n return {\n code: \"reporter_failure\",\n severity: \"error\",\n message,\n ...(target === undefined ? {} : { target }),\n };\n}\n\nfunction slugForPathLabel(value: string): string {\n const base = path.basename(value)\n .replace(/\\.(test|spec)\\.[^.]+$/, \"\")\n .replace(/\\.[^.]+$/, \"\");\n const slug = base\n .toLowerCase()\n .replace(/[^a-z0-9._-]+/g, \"-\")\n .replace(/^[._-]+|[._-]+$/g, \"\")\n .slice(0, 80);\n return slug.length > 0 ? slug : \"artifact\";\n}\n\n/**\n * Standard Evidence v2 filenames for CI failure packages (same shape as `bundle`).\n * Success remains quiet by default — callers should emit these only on failure.\n */\nexport const EVIDENCE_CI_ARTIFACT_FILES = [\n \"evidence.html\",\n \"evidence.json\",\n \"check-results.json\",\n \"trace.jsonl\",\n] as const;\n\nexport type EvidenceCiArtifactFile = (typeof EVIDENCE_CI_ARTIFACT_FILES)[number];\n\n/**\n * Experimental helper: TraceArtifact entries for a standard Evidence v2 CI package.\n */\nexport function createEvidenceCiArtifacts(options: {\n redactionProfile?: TraceArtifactRedactionProfile;\n /** Optional subdirectory under the test artifact folder (POSIX). */\n relativeDir?: string;\n}): TraceArtifact[] {\n const profile = options.redactionProfile ?? \"share\";\n const prefix =\n options.relativeDir !== undefined && options.relativeDir.trim() !== \"\"\n ? options.relativeDir.replace(/\\\\/g, \"/\").replace(/^\\/+|\\/+$/g, \"\")\n : \"\";\n const join = (name: string): string => (prefix === \"\" ? name : path.posix.join(prefix, name));\n\n const formatFor = (name: EvidenceCiArtifactFile): TraceArtifactFormat => {\n if (name.endsWith(\".html\")) return \"html\";\n if (name.endsWith(\".jsonl\")) return \"jsonl\";\n return \"json\";\n };\n\n return EVIDENCE_CI_ARTIFACT_FILES.map((name) => ({\n kind: \"evidence\" as const,\n path: join(name),\n format: formatFor(name),\n redactionProfile: profile,\n title: `Evidence v2 ${name}`,\n }));\n}\n"]}