@dotsetlabs/bellwether 0.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.
- package/CHANGELOG.md +291 -0
- package/LICENSE +21 -0
- package/README.md +739 -0
- package/dist/auth/credentials.d.ts +64 -0
- package/dist/auth/credentials.js +218 -0
- package/dist/auth/index.d.ts +6 -0
- package/dist/auth/index.js +6 -0
- package/dist/auth/keychain.d.ts +64 -0
- package/dist/auth/keychain.js +268 -0
- package/dist/baseline/ab-testing.d.ts +80 -0
- package/dist/baseline/ab-testing.js +236 -0
- package/dist/baseline/ai-compatibility-scorer.d.ts +95 -0
- package/dist/baseline/ai-compatibility-scorer.js +606 -0
- package/dist/baseline/calibration.d.ts +77 -0
- package/dist/baseline/calibration.js +136 -0
- package/dist/baseline/category-matching.d.ts +85 -0
- package/dist/baseline/category-matching.js +289 -0
- package/dist/baseline/change-impact-analyzer.d.ts +98 -0
- package/dist/baseline/change-impact-analyzer.js +592 -0
- package/dist/baseline/comparator.d.ts +64 -0
- package/dist/baseline/comparator.js +916 -0
- package/dist/baseline/confidence.d.ts +55 -0
- package/dist/baseline/confidence.js +122 -0
- package/dist/baseline/converter.d.ts +61 -0
- package/dist/baseline/converter.js +585 -0
- package/dist/baseline/dependency-analyzer.d.ts +89 -0
- package/dist/baseline/dependency-analyzer.js +567 -0
- package/dist/baseline/deprecation-tracker.d.ts +133 -0
- package/dist/baseline/deprecation-tracker.js +322 -0
- package/dist/baseline/diff.d.ts +55 -0
- package/dist/baseline/diff.js +1584 -0
- package/dist/baseline/documentation-scorer.d.ts +205 -0
- package/dist/baseline/documentation-scorer.js +466 -0
- package/dist/baseline/embeddings.d.ts +118 -0
- package/dist/baseline/embeddings.js +251 -0
- package/dist/baseline/error-analyzer.d.ts +198 -0
- package/dist/baseline/error-analyzer.js +721 -0
- package/dist/baseline/evaluation/evaluator.d.ts +42 -0
- package/dist/baseline/evaluation/evaluator.js +323 -0
- package/dist/baseline/evaluation/expanded-dataset.d.ts +45 -0
- package/dist/baseline/evaluation/expanded-dataset.js +1164 -0
- package/dist/baseline/evaluation/golden-dataset.d.ts +58 -0
- package/dist/baseline/evaluation/golden-dataset.js +717 -0
- package/dist/baseline/evaluation/index.d.ts +15 -0
- package/dist/baseline/evaluation/index.js +15 -0
- package/dist/baseline/evaluation/types.d.ts +186 -0
- package/dist/baseline/evaluation/types.js +8 -0
- package/dist/baseline/external-dependency-detector.d.ts +181 -0
- package/dist/baseline/external-dependency-detector.js +524 -0
- package/dist/baseline/golden-output.d.ts +162 -0
- package/dist/baseline/golden-output.js +636 -0
- package/dist/baseline/health-scorer.d.ts +174 -0
- package/dist/baseline/health-scorer.js +451 -0
- package/dist/baseline/incremental-checker.d.ts +97 -0
- package/dist/baseline/incremental-checker.js +174 -0
- package/dist/baseline/index.d.ts +31 -0
- package/dist/baseline/index.js +42 -0
- package/dist/baseline/migration-generator.d.ts +137 -0
- package/dist/baseline/migration-generator.js +554 -0
- package/dist/baseline/migrations.d.ts +60 -0
- package/dist/baseline/migrations.js +197 -0
- package/dist/baseline/performance-tracker.d.ts +214 -0
- package/dist/baseline/performance-tracker.js +577 -0
- package/dist/baseline/pr-comment-generator.d.ts +117 -0
- package/dist/baseline/pr-comment-generator.js +546 -0
- package/dist/baseline/response-fingerprint.d.ts +127 -0
- package/dist/baseline/response-fingerprint.js +728 -0
- package/dist/baseline/response-schema-tracker.d.ts +129 -0
- package/dist/baseline/response-schema-tracker.js +420 -0
- package/dist/baseline/risk-scorer.d.ts +54 -0
- package/dist/baseline/risk-scorer.js +434 -0
- package/dist/baseline/saver.d.ts +89 -0
- package/dist/baseline/saver.js +554 -0
- package/dist/baseline/scenario-generator.d.ts +151 -0
- package/dist/baseline/scenario-generator.js +905 -0
- package/dist/baseline/schema-compare.d.ts +86 -0
- package/dist/baseline/schema-compare.js +557 -0
- package/dist/baseline/schema-evolution.d.ts +189 -0
- package/dist/baseline/schema-evolution.js +467 -0
- package/dist/baseline/semantic.d.ts +203 -0
- package/dist/baseline/semantic.js +908 -0
- package/dist/baseline/synonyms.d.ts +60 -0
- package/dist/baseline/synonyms.js +386 -0
- package/dist/baseline/telemetry.d.ts +165 -0
- package/dist/baseline/telemetry.js +294 -0
- package/dist/baseline/test-pruner.d.ts +120 -0
- package/dist/baseline/test-pruner.js +387 -0
- package/dist/baseline/types.d.ts +449 -0
- package/dist/baseline/types.js +5 -0
- package/dist/baseline/version.d.ts +138 -0
- package/dist/baseline/version.js +206 -0
- package/dist/cache/index.d.ts +5 -0
- package/dist/cache/index.js +5 -0
- package/dist/cache/response-cache.d.ts +151 -0
- package/dist/cache/response-cache.js +287 -0
- package/dist/ci/index.d.ts +60 -0
- package/dist/ci/index.js +342 -0
- package/dist/cli/commands/auth.d.ts +12 -0
- package/dist/cli/commands/auth.js +352 -0
- package/dist/cli/commands/badge.d.ts +3 -0
- package/dist/cli/commands/badge.js +74 -0
- package/dist/cli/commands/baseline-accept.d.ts +15 -0
- package/dist/cli/commands/baseline-accept.js +178 -0
- package/dist/cli/commands/baseline-migrate.d.ts +12 -0
- package/dist/cli/commands/baseline-migrate.js +164 -0
- package/dist/cli/commands/baseline.d.ts +14 -0
- package/dist/cli/commands/baseline.js +449 -0
- package/dist/cli/commands/beta.d.ts +10 -0
- package/dist/cli/commands/beta.js +231 -0
- package/dist/cli/commands/check.d.ts +11 -0
- package/dist/cli/commands/check.js +820 -0
- package/dist/cli/commands/cloud/badge.d.ts +3 -0
- package/dist/cli/commands/cloud/badge.js +74 -0
- package/dist/cli/commands/cloud/diff.d.ts +6 -0
- package/dist/cli/commands/cloud/diff.js +79 -0
- package/dist/cli/commands/cloud/history.d.ts +6 -0
- package/dist/cli/commands/cloud/history.js +102 -0
- package/dist/cli/commands/cloud/link.d.ts +9 -0
- package/dist/cli/commands/cloud/link.js +119 -0
- package/dist/cli/commands/cloud/login.d.ts +7 -0
- package/dist/cli/commands/cloud/login.js +499 -0
- package/dist/cli/commands/cloud/projects.d.ts +6 -0
- package/dist/cli/commands/cloud/projects.js +44 -0
- package/dist/cli/commands/cloud/shared.d.ts +7 -0
- package/dist/cli/commands/cloud/shared.js +42 -0
- package/dist/cli/commands/cloud/teams.d.ts +8 -0
- package/dist/cli/commands/cloud/teams.js +169 -0
- package/dist/cli/commands/cloud/upload.d.ts +8 -0
- package/dist/cli/commands/cloud/upload.js +181 -0
- package/dist/cli/commands/contract.d.ts +11 -0
- package/dist/cli/commands/contract.js +280 -0
- package/dist/cli/commands/discover.d.ts +3 -0
- package/dist/cli/commands/discover.js +82 -0
- package/dist/cli/commands/eval.d.ts +9 -0
- package/dist/cli/commands/eval.js +187 -0
- package/dist/cli/commands/explore.d.ts +11 -0
- package/dist/cli/commands/explore.js +437 -0
- package/dist/cli/commands/feedback.d.ts +9 -0
- package/dist/cli/commands/feedback.js +174 -0
- package/dist/cli/commands/golden.d.ts +12 -0
- package/dist/cli/commands/golden.js +407 -0
- package/dist/cli/commands/history.d.ts +10 -0
- package/dist/cli/commands/history.js +202 -0
- package/dist/cli/commands/init.d.ts +9 -0
- package/dist/cli/commands/init.js +219 -0
- package/dist/cli/commands/interview.d.ts +3 -0
- package/dist/cli/commands/interview.js +903 -0
- package/dist/cli/commands/link.d.ts +10 -0
- package/dist/cli/commands/link.js +169 -0
- package/dist/cli/commands/login.d.ts +7 -0
- package/dist/cli/commands/login.js +499 -0
- package/dist/cli/commands/preset.d.ts +33 -0
- package/dist/cli/commands/preset.js +297 -0
- package/dist/cli/commands/profile.d.ts +33 -0
- package/dist/cli/commands/profile.js +286 -0
- package/dist/cli/commands/registry.d.ts +11 -0
- package/dist/cli/commands/registry.js +146 -0
- package/dist/cli/commands/shared.d.ts +79 -0
- package/dist/cli/commands/shared.js +196 -0
- package/dist/cli/commands/teams.d.ts +8 -0
- package/dist/cli/commands/teams.js +169 -0
- package/dist/cli/commands/test.d.ts +9 -0
- package/dist/cli/commands/test.js +500 -0
- package/dist/cli/commands/upload.d.ts +8 -0
- package/dist/cli/commands/upload.js +223 -0
- package/dist/cli/commands/validate-config.d.ts +6 -0
- package/dist/cli/commands/validate-config.js +35 -0
- package/dist/cli/commands/verify.d.ts +11 -0
- package/dist/cli/commands/verify.js +283 -0
- package/dist/cli/commands/watch.d.ts +12 -0
- package/dist/cli/commands/watch.js +253 -0
- package/dist/cli/index.d.ts +3 -0
- package/dist/cli/index.js +178 -0
- package/dist/cli/interactive.d.ts +47 -0
- package/dist/cli/interactive.js +216 -0
- package/dist/cli/output/terminal-reporter.d.ts +19 -0
- package/dist/cli/output/terminal-reporter.js +104 -0
- package/dist/cli/output.d.ts +226 -0
- package/dist/cli/output.js +438 -0
- package/dist/cli/utils/env.d.ts +5 -0
- package/dist/cli/utils/env.js +14 -0
- package/dist/cli/utils/progress.d.ts +59 -0
- package/dist/cli/utils/progress.js +206 -0
- package/dist/cli/utils/server-context.d.ts +10 -0
- package/dist/cli/utils/server-context.js +36 -0
- package/dist/cloud/auth.d.ts +144 -0
- package/dist/cloud/auth.js +374 -0
- package/dist/cloud/client.d.ts +24 -0
- package/dist/cloud/client.js +65 -0
- package/dist/cloud/http-client.d.ts +38 -0
- package/dist/cloud/http-client.js +215 -0
- package/dist/cloud/index.d.ts +23 -0
- package/dist/cloud/index.js +25 -0
- package/dist/cloud/mock-client.d.ts +107 -0
- package/dist/cloud/mock-client.js +545 -0
- package/dist/cloud/types.d.ts +515 -0
- package/dist/cloud/types.js +15 -0
- package/dist/config/defaults.d.ts +160 -0
- package/dist/config/defaults.js +169 -0
- package/dist/config/loader.d.ts +24 -0
- package/dist/config/loader.js +122 -0
- package/dist/config/template.d.ts +42 -0
- package/dist/config/template.js +647 -0
- package/dist/config/validator.d.ts +2112 -0
- package/dist/config/validator.js +658 -0
- package/dist/constants/cloud.d.ts +107 -0
- package/dist/constants/cloud.js +110 -0
- package/dist/constants/core.d.ts +521 -0
- package/dist/constants/core.js +556 -0
- package/dist/constants/testing.d.ts +1283 -0
- package/dist/constants/testing.js +1568 -0
- package/dist/constants.d.ts +10 -0
- package/dist/constants.js +10 -0
- package/dist/contract/index.d.ts +6 -0
- package/dist/contract/index.js +5 -0
- package/dist/contract/validator.d.ts +177 -0
- package/dist/contract/validator.js +574 -0
- package/dist/cost/index.d.ts +6 -0
- package/dist/cost/index.js +5 -0
- package/dist/cost/tracker.d.ts +134 -0
- package/dist/cost/tracker.js +313 -0
- package/dist/discovery/discovery.d.ts +16 -0
- package/dist/discovery/discovery.js +173 -0
- package/dist/discovery/types.d.ts +51 -0
- package/dist/discovery/types.js +2 -0
- package/dist/docs/agents.d.ts +3 -0
- package/dist/docs/agents.js +995 -0
- package/dist/docs/contract.d.ts +51 -0
- package/dist/docs/contract.js +1681 -0
- package/dist/docs/generator.d.ts +4 -0
- package/dist/docs/generator.js +4 -0
- package/dist/docs/html-reporter.d.ts +9 -0
- package/dist/docs/html-reporter.js +757 -0
- package/dist/docs/index.d.ts +10 -0
- package/dist/docs/index.js +11 -0
- package/dist/docs/junit-reporter.d.ts +18 -0
- package/dist/docs/junit-reporter.js +210 -0
- package/dist/docs/report.d.ts +14 -0
- package/dist/docs/report.js +44 -0
- package/dist/docs/sarif-reporter.d.ts +19 -0
- package/dist/docs/sarif-reporter.js +335 -0
- package/dist/docs/shared.d.ts +35 -0
- package/dist/docs/shared.js +162 -0
- package/dist/docs/templates.d.ts +12 -0
- package/dist/docs/templates.js +76 -0
- package/dist/errors/index.d.ts +6 -0
- package/dist/errors/index.js +6 -0
- package/dist/errors/retry.d.ts +92 -0
- package/dist/errors/retry.js +323 -0
- package/dist/errors/types.d.ts +321 -0
- package/dist/errors/types.js +584 -0
- package/dist/index.d.ts +32 -0
- package/dist/index.js +32 -0
- package/dist/interview/dependency-resolver.d.ts +11 -0
- package/dist/interview/dependency-resolver.js +32 -0
- package/dist/interview/interviewer.d.ts +232 -0
- package/dist/interview/interviewer.js +1939 -0
- package/dist/interview/mock-response-generator.d.ts +7 -0
- package/dist/interview/mock-response-generator.js +102 -0
- package/dist/interview/orchestrator.d.ts +237 -0
- package/dist/interview/orchestrator.js +1296 -0
- package/dist/interview/rate-limiter.d.ts +15 -0
- package/dist/interview/rate-limiter.js +55 -0
- package/dist/interview/response-validator.d.ts +10 -0
- package/dist/interview/response-validator.js +132 -0
- package/dist/interview/schema-inferrer.d.ts +8 -0
- package/dist/interview/schema-inferrer.js +71 -0
- package/dist/interview/schema-test-generator.d.ts +71 -0
- package/dist/interview/schema-test-generator.js +834 -0
- package/dist/interview/smart-value-generator.d.ts +155 -0
- package/dist/interview/smart-value-generator.js +554 -0
- package/dist/interview/stateful-test-runner.d.ts +19 -0
- package/dist/interview/stateful-test-runner.js +106 -0
- package/dist/interview/types.d.ts +561 -0
- package/dist/interview/types.js +2 -0
- package/dist/llm/anthropic.d.ts +41 -0
- package/dist/llm/anthropic.js +355 -0
- package/dist/llm/client.d.ts +123 -0
- package/dist/llm/client.js +42 -0
- package/dist/llm/factory.d.ts +38 -0
- package/dist/llm/factory.js +145 -0
- package/dist/llm/fallback.d.ts +140 -0
- package/dist/llm/fallback.js +379 -0
- package/dist/llm/index.d.ts +18 -0
- package/dist/llm/index.js +15 -0
- package/dist/llm/ollama.d.ts +37 -0
- package/dist/llm/ollama.js +330 -0
- package/dist/llm/openai.d.ts +25 -0
- package/dist/llm/openai.js +320 -0
- package/dist/llm/token-budget.d.ts +161 -0
- package/dist/llm/token-budget.js +395 -0
- package/dist/logging/logger.d.ts +70 -0
- package/dist/logging/logger.js +130 -0
- package/dist/metrics/collector.d.ts +106 -0
- package/dist/metrics/collector.js +547 -0
- package/dist/metrics/index.d.ts +7 -0
- package/dist/metrics/index.js +7 -0
- package/dist/metrics/prometheus.d.ts +20 -0
- package/dist/metrics/prometheus.js +241 -0
- package/dist/metrics/types.d.ts +209 -0
- package/dist/metrics/types.js +5 -0
- package/dist/persona/builtins.d.ts +54 -0
- package/dist/persona/builtins.js +219 -0
- package/dist/persona/index.d.ts +8 -0
- package/dist/persona/index.js +8 -0
- package/dist/persona/loader.d.ts +30 -0
- package/dist/persona/loader.js +190 -0
- package/dist/persona/types.d.ts +144 -0
- package/dist/persona/types.js +5 -0
- package/dist/persona/validation.d.ts +94 -0
- package/dist/persona/validation.js +332 -0
- package/dist/prompts/index.d.ts +5 -0
- package/dist/prompts/index.js +5 -0
- package/dist/prompts/templates.d.ts +180 -0
- package/dist/prompts/templates.js +431 -0
- package/dist/registry/client.d.ts +49 -0
- package/dist/registry/client.js +191 -0
- package/dist/registry/index.d.ts +7 -0
- package/dist/registry/index.js +6 -0
- package/dist/registry/types.d.ts +140 -0
- package/dist/registry/types.js +6 -0
- package/dist/scenarios/evaluator.d.ts +43 -0
- package/dist/scenarios/evaluator.js +206 -0
- package/dist/scenarios/index.d.ts +10 -0
- package/dist/scenarios/index.js +9 -0
- package/dist/scenarios/loader.d.ts +20 -0
- package/dist/scenarios/loader.js +285 -0
- package/dist/scenarios/types.d.ts +153 -0
- package/dist/scenarios/types.js +8 -0
- package/dist/security/index.d.ts +17 -0
- package/dist/security/index.js +18 -0
- package/dist/security/payloads.d.ts +61 -0
- package/dist/security/payloads.js +268 -0
- package/dist/security/security-tester.d.ts +42 -0
- package/dist/security/security-tester.js +582 -0
- package/dist/security/types.d.ts +166 -0
- package/dist/security/types.js +8 -0
- package/dist/transport/base-transport.d.ts +59 -0
- package/dist/transport/base-transport.js +38 -0
- package/dist/transport/http-transport.d.ts +67 -0
- package/dist/transport/http-transport.js +238 -0
- package/dist/transport/mcp-client.d.ts +141 -0
- package/dist/transport/mcp-client.js +496 -0
- package/dist/transport/sse-transport.d.ts +88 -0
- package/dist/transport/sse-transport.js +316 -0
- package/dist/transport/stdio-transport.d.ts +43 -0
- package/dist/transport/stdio-transport.js +238 -0
- package/dist/transport/types.d.ts +125 -0
- package/dist/transport/types.js +16 -0
- package/dist/utils/concurrency.d.ts +123 -0
- package/dist/utils/concurrency.js +213 -0
- package/dist/utils/formatters.d.ts +16 -0
- package/dist/utils/formatters.js +37 -0
- package/dist/utils/index.d.ts +8 -0
- package/dist/utils/index.js +8 -0
- package/dist/utils/jsonpath.d.ts +87 -0
- package/dist/utils/jsonpath.js +326 -0
- package/dist/utils/markdown.d.ts +113 -0
- package/dist/utils/markdown.js +265 -0
- package/dist/utils/network.d.ts +14 -0
- package/dist/utils/network.js +17 -0
- package/dist/utils/sanitize.d.ts +92 -0
- package/dist/utils/sanitize.js +191 -0
- package/dist/utils/semantic.d.ts +194 -0
- package/dist/utils/semantic.js +1051 -0
- package/dist/utils/smart-truncate.d.ts +94 -0
- package/dist/utils/smart-truncate.js +361 -0
- package/dist/utils/timeout.d.ts +153 -0
- package/dist/utils/timeout.js +205 -0
- package/dist/utils/yaml-parser.d.ts +58 -0
- package/dist/utils/yaml-parser.js +86 -0
- package/dist/validation/index.d.ts +32 -0
- package/dist/validation/index.js +32 -0
- package/dist/validation/semantic-test-generator.d.ts +50 -0
- package/dist/validation/semantic-test-generator.js +176 -0
- package/dist/validation/semantic-types.d.ts +66 -0
- package/dist/validation/semantic-types.js +94 -0
- package/dist/validation/semantic-validator.d.ts +38 -0
- package/dist/validation/semantic-validator.js +340 -0
- package/dist/verification/index.d.ts +6 -0
- package/dist/verification/index.js +5 -0
- package/dist/verification/types.d.ts +133 -0
- package/dist/verification/types.js +5 -0
- package/dist/verification/verifier.d.ts +30 -0
- package/dist/verification/verifier.js +309 -0
- package/dist/version.d.ts +19 -0
- package/dist/version.js +48 -0
- package/dist/workflow/auto-generator.d.ts +27 -0
- package/dist/workflow/auto-generator.js +513 -0
- package/dist/workflow/discovery.d.ts +40 -0
- package/dist/workflow/discovery.js +195 -0
- package/dist/workflow/executor.d.ts +82 -0
- package/dist/workflow/executor.js +611 -0
- package/dist/workflow/index.d.ts +10 -0
- package/dist/workflow/index.js +10 -0
- package/dist/workflow/loader.d.ts +24 -0
- package/dist/workflow/loader.js +194 -0
- package/dist/workflow/state-tracker.d.ts +98 -0
- package/dist/workflow/state-tracker.js +424 -0
- package/dist/workflow/types.d.ts +337 -0
- package/dist/workflow/types.js +5 -0
- package/package.json +94 -0
- package/schemas/bellwether-check.schema.json +651 -0
|
@@ -0,0 +1,129 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Response schema evolution tracking.
|
|
3
|
+
*
|
|
4
|
+
* Tracks response schema consistency across runs and detects when tools
|
|
5
|
+
* return different field structures, enabling schema evolution analysis
|
|
6
|
+
* for drift detection.
|
|
7
|
+
*/
|
|
8
|
+
import type { InferredSchema } from './response-fingerprint.js';
|
|
9
|
+
/**
|
|
10
|
+
* Response schema evolution record.
|
|
11
|
+
* Tracks schema stability and inconsistencies across samples.
|
|
12
|
+
*/
|
|
13
|
+
export interface ResponseSchemaEvolution {
|
|
14
|
+
/** Current schema hash */
|
|
15
|
+
currentHash: string;
|
|
16
|
+
/** Historical schema hashes (most recent first) */
|
|
17
|
+
history: SchemaVersion[];
|
|
18
|
+
/** Whether schema has been stable across all samples */
|
|
19
|
+
isStable: boolean;
|
|
20
|
+
/** Confidence in schema stability (0-1) */
|
|
21
|
+
stabilityConfidence: number;
|
|
22
|
+
/** Fields that appear inconsistently */
|
|
23
|
+
inconsistentFields: string[];
|
|
24
|
+
/** Total number of samples analyzed */
|
|
25
|
+
sampleCount: number;
|
|
26
|
+
}
|
|
27
|
+
/**
|
|
28
|
+
* A historical schema version.
|
|
29
|
+
*/
|
|
30
|
+
export interface SchemaVersion {
|
|
31
|
+
/** Schema hash */
|
|
32
|
+
hash: string;
|
|
33
|
+
/** The schema at this version */
|
|
34
|
+
schema: InferredSchema;
|
|
35
|
+
/** When this version was observed */
|
|
36
|
+
observedAt: Date;
|
|
37
|
+
/** Number of samples with this version */
|
|
38
|
+
sampleCount: number;
|
|
39
|
+
}
|
|
40
|
+
/**
|
|
41
|
+
* Schema comparison result for evolution detection.
|
|
42
|
+
*/
|
|
43
|
+
export interface SchemaEvolutionDiff {
|
|
44
|
+
/** Whether schema structure changed */
|
|
45
|
+
structureChanged: boolean;
|
|
46
|
+
/** Fields added in new schema */
|
|
47
|
+
fieldsAdded: string[];
|
|
48
|
+
/** Fields removed from schema */
|
|
49
|
+
fieldsRemoved: string[];
|
|
50
|
+
/** Fields with type changes */
|
|
51
|
+
typeChanges: SchemaTypeChange[];
|
|
52
|
+
/** Fields that became required */
|
|
53
|
+
newRequired: string[];
|
|
54
|
+
/** Fields that became optional */
|
|
55
|
+
newOptional: string[];
|
|
56
|
+
/** Backward compatibility assessment */
|
|
57
|
+
backwardCompatible: boolean;
|
|
58
|
+
/** Whether the change is breaking for consumers */
|
|
59
|
+
isBreaking: boolean;
|
|
60
|
+
/** Human-readable summary of changes */
|
|
61
|
+
summary: string;
|
|
62
|
+
}
|
|
63
|
+
/**
|
|
64
|
+
* A type change for a field.
|
|
65
|
+
*/
|
|
66
|
+
export interface SchemaTypeChange {
|
|
67
|
+
/** Field path (dot notation for nested fields) */
|
|
68
|
+
field: string;
|
|
69
|
+
/** Previous type */
|
|
70
|
+
previousType: string;
|
|
71
|
+
/** Current type */
|
|
72
|
+
currentType: string;
|
|
73
|
+
/** Whether this change is backward compatible */
|
|
74
|
+
backwardCompatible: boolean;
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Compare two inferred schemas for evolution.
|
|
78
|
+
*
|
|
79
|
+
* @param previous - Previous schema (or undefined if new)
|
|
80
|
+
* @param current - Current schema (or undefined if removed)
|
|
81
|
+
* @returns Detailed comparison result
|
|
82
|
+
*/
|
|
83
|
+
export declare function compareInferredSchemas(previous: InferredSchema | undefined, current: InferredSchema | undefined): SchemaEvolutionDiff;
|
|
84
|
+
/**
|
|
85
|
+
* Build response schema evolution from multiple samples.
|
|
86
|
+
*
|
|
87
|
+
* @param schemas - Array of inferred schemas from samples
|
|
88
|
+
* @returns Schema evolution record
|
|
89
|
+
*/
|
|
90
|
+
export declare function buildSchemaEvolution(schemas: InferredSchema[]): ResponseSchemaEvolution;
|
|
91
|
+
/**
|
|
92
|
+
* Compare schema evolution records between baselines.
|
|
93
|
+
*
|
|
94
|
+
* @param previous - Previous schema evolution
|
|
95
|
+
* @param current - Current schema evolution
|
|
96
|
+
* @returns Evolution comparison result
|
|
97
|
+
*/
|
|
98
|
+
export declare function compareSchemaEvolution(previous: ResponseSchemaEvolution | undefined, current: ResponseSchemaEvolution | undefined): SchemaEvolutionDiff;
|
|
99
|
+
/**
|
|
100
|
+
* Format schema evolution for display.
|
|
101
|
+
*
|
|
102
|
+
* @param evolution - Schema evolution record
|
|
103
|
+
* @returns Formatted string representation
|
|
104
|
+
*/
|
|
105
|
+
export declare function formatSchemaEvolution(evolution: ResponseSchemaEvolution): string;
|
|
106
|
+
/**
|
|
107
|
+
* Format schema evolution diff for display.
|
|
108
|
+
*
|
|
109
|
+
* @param diff - Schema evolution diff
|
|
110
|
+
* @param useColors - Whether to use ANSI colors
|
|
111
|
+
* @returns Formatted string representation
|
|
112
|
+
*/
|
|
113
|
+
export declare function formatSchemaEvolutionDiff(diff: SchemaEvolutionDiff, useColors?: boolean): string[];
|
|
114
|
+
/**
|
|
115
|
+
* Determine if schema evolution indicates breaking changes.
|
|
116
|
+
*
|
|
117
|
+
* @param evolution - Schema evolution record
|
|
118
|
+
* @param threshold - Confidence threshold for stability
|
|
119
|
+
* @returns Whether the schema evolution indicates issues
|
|
120
|
+
*/
|
|
121
|
+
export declare function hasSchemaEvolutionIssues(evolution: ResponseSchemaEvolution, threshold?: number): boolean;
|
|
122
|
+
/**
|
|
123
|
+
* Get schema evolution stability grade.
|
|
124
|
+
*
|
|
125
|
+
* @param evolution - Schema evolution record
|
|
126
|
+
* @returns Grade from A-F
|
|
127
|
+
*/
|
|
128
|
+
export declare function getSchemaStabilityGrade(evolution: ResponseSchemaEvolution): 'A' | 'B' | 'C' | 'D' | 'F' | 'N/A';
|
|
129
|
+
//# sourceMappingURL=response-schema-tracker.d.ts.map
|
|
@@ -0,0 +1,420 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Response schema evolution tracking.
|
|
3
|
+
*
|
|
4
|
+
* Tracks response schema consistency across runs and detects when tools
|
|
5
|
+
* return different field structures, enabling schema evolution analysis
|
|
6
|
+
* for drift detection.
|
|
7
|
+
*/
|
|
8
|
+
import { computeInferredSchemaHash } from './response-fingerprint.js';
|
|
9
|
+
import { SCHEMA_EVOLUTION } from '../constants.js';
|
|
10
|
+
/**
|
|
11
|
+
* Compare two inferred schemas for evolution.
|
|
12
|
+
*
|
|
13
|
+
* @param previous - Previous schema (or undefined if new)
|
|
14
|
+
* @param current - Current schema (or undefined if removed)
|
|
15
|
+
* @returns Detailed comparison result
|
|
16
|
+
*/
|
|
17
|
+
export function compareInferredSchemas(previous, current) {
|
|
18
|
+
// Both undefined - no change
|
|
19
|
+
if (!previous && !current) {
|
|
20
|
+
return createEmptyDiff();
|
|
21
|
+
}
|
|
22
|
+
// Schema added (new tool or first response)
|
|
23
|
+
if (!previous) {
|
|
24
|
+
const fields = current?.properties ? Object.keys(current.properties) : [];
|
|
25
|
+
return {
|
|
26
|
+
structureChanged: fields.length > 0,
|
|
27
|
+
fieldsAdded: fields,
|
|
28
|
+
fieldsRemoved: [],
|
|
29
|
+
typeChanges: [],
|
|
30
|
+
newRequired: current?.required ?? [],
|
|
31
|
+
newOptional: [],
|
|
32
|
+
backwardCompatible: true, // Adding fields is backward compatible
|
|
33
|
+
isBreaking: false,
|
|
34
|
+
summary: fields.length > 0
|
|
35
|
+
? `Schema established with ${fields.length} field(s)`
|
|
36
|
+
: 'Empty schema established',
|
|
37
|
+
};
|
|
38
|
+
}
|
|
39
|
+
// Schema removed
|
|
40
|
+
if (!current) {
|
|
41
|
+
const fields = previous.properties ? Object.keys(previous.properties) : [];
|
|
42
|
+
return {
|
|
43
|
+
structureChanged: fields.length > 0,
|
|
44
|
+
fieldsAdded: [],
|
|
45
|
+
fieldsRemoved: fields,
|
|
46
|
+
typeChanges: [],
|
|
47
|
+
newRequired: [],
|
|
48
|
+
newOptional: [],
|
|
49
|
+
backwardCompatible: false, // Removing all fields is breaking
|
|
50
|
+
isBreaking: true,
|
|
51
|
+
summary: fields.length > 0
|
|
52
|
+
? `Schema removed (${fields.length} field(s) lost)`
|
|
53
|
+
: 'Schema removed',
|
|
54
|
+
};
|
|
55
|
+
}
|
|
56
|
+
// Both schemas exist - compare them
|
|
57
|
+
return compareSchemaStructures(previous, current);
|
|
58
|
+
}
|
|
59
|
+
/**
|
|
60
|
+
* Compare two schema structures in detail.
|
|
61
|
+
*/
|
|
62
|
+
function compareSchemaStructures(previous, current) {
|
|
63
|
+
const prevFields = new Set(Object.keys(previous.properties ?? {}));
|
|
64
|
+
const currFields = new Set(Object.keys(current.properties ?? {}));
|
|
65
|
+
const fieldsAdded = [...currFields].filter(f => !prevFields.has(f));
|
|
66
|
+
const fieldsRemoved = [...prevFields].filter(f => !currFields.has(f));
|
|
67
|
+
// Check for type changes in common fields
|
|
68
|
+
const typeChanges = [];
|
|
69
|
+
for (const field of prevFields) {
|
|
70
|
+
if (currFields.has(field)) {
|
|
71
|
+
const prevProp = previous.properties?.[field];
|
|
72
|
+
const currProp = current.properties?.[field];
|
|
73
|
+
if (prevProp && currProp && prevProp.type !== currProp.type) {
|
|
74
|
+
const isCompatible = isTypeChangeCompatible(prevProp.type, currProp.type);
|
|
75
|
+
typeChanges.push({
|
|
76
|
+
field,
|
|
77
|
+
previousType: prevProp.type,
|
|
78
|
+
currentType: currProp.type,
|
|
79
|
+
backwardCompatible: isCompatible,
|
|
80
|
+
});
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
// Check required field changes
|
|
85
|
+
const prevRequired = new Set(previous.required ?? []);
|
|
86
|
+
const currRequired = new Set(current.required ?? []);
|
|
87
|
+
const newRequired = [...currRequired].filter(f => !prevRequired.has(f) && prevFields.has(f));
|
|
88
|
+
const newOptional = [...prevRequired].filter(f => !currRequired.has(f) && currFields.has(f));
|
|
89
|
+
const structureChanged = fieldsAdded.length > 0 ||
|
|
90
|
+
fieldsRemoved.length > 0 ||
|
|
91
|
+
typeChanges.length > 0 ||
|
|
92
|
+
newRequired.length > 0 ||
|
|
93
|
+
newOptional.length > 0;
|
|
94
|
+
// Backward compatible if:
|
|
95
|
+
// - No fields removed
|
|
96
|
+
// - No breaking type changes
|
|
97
|
+
// - No new required fields on existing fields
|
|
98
|
+
const backwardCompatible = fieldsRemoved.length === 0 &&
|
|
99
|
+
typeChanges.every(tc => tc.backwardCompatible) &&
|
|
100
|
+
newRequired.length === 0;
|
|
101
|
+
// Breaking if:
|
|
102
|
+
// - Fields removed
|
|
103
|
+
// - Breaking type changes
|
|
104
|
+
// - New required fields (consumers may not provide them)
|
|
105
|
+
const isBreaking = fieldsRemoved.length > 0 ||
|
|
106
|
+
typeChanges.some(tc => !tc.backwardCompatible) ||
|
|
107
|
+
newRequired.length > 0;
|
|
108
|
+
// Build summary
|
|
109
|
+
const summary = buildChangeSummary({
|
|
110
|
+
fieldsAdded,
|
|
111
|
+
fieldsRemoved,
|
|
112
|
+
typeChanges,
|
|
113
|
+
newRequired,
|
|
114
|
+
newOptional,
|
|
115
|
+
});
|
|
116
|
+
return {
|
|
117
|
+
structureChanged,
|
|
118
|
+
fieldsAdded,
|
|
119
|
+
fieldsRemoved,
|
|
120
|
+
typeChanges,
|
|
121
|
+
newRequired,
|
|
122
|
+
newOptional,
|
|
123
|
+
backwardCompatible,
|
|
124
|
+
isBreaking,
|
|
125
|
+
summary,
|
|
126
|
+
};
|
|
127
|
+
}
|
|
128
|
+
/**
|
|
129
|
+
* Check if a type change is backward compatible.
|
|
130
|
+
*/
|
|
131
|
+
function isTypeChangeCompatible(prevType, currType) {
|
|
132
|
+
// Widening type changes are compatible (more permissive)
|
|
133
|
+
const wideningChanges = {
|
|
134
|
+
'integer': ['number'], // integer -> number is compatible
|
|
135
|
+
'null': ['string', 'number', 'integer', 'boolean', 'object', 'array'], // null -> anything
|
|
136
|
+
};
|
|
137
|
+
if (wideningChanges[prevType]?.includes(currType)) {
|
|
138
|
+
return true;
|
|
139
|
+
}
|
|
140
|
+
// Adding nullable is compatible
|
|
141
|
+
if (prevType !== 'null' && currType === 'mixed') {
|
|
142
|
+
return true;
|
|
143
|
+
}
|
|
144
|
+
return false;
|
|
145
|
+
}
|
|
146
|
+
/**
|
|
147
|
+
* Build a human-readable summary of schema changes.
|
|
148
|
+
*/
|
|
149
|
+
function buildChangeSummary(changes) {
|
|
150
|
+
const parts = [];
|
|
151
|
+
if (changes.fieldsRemoved.length > 0) {
|
|
152
|
+
parts.push(`${changes.fieldsRemoved.length} field(s) removed`);
|
|
153
|
+
}
|
|
154
|
+
if (changes.fieldsAdded.length > 0) {
|
|
155
|
+
parts.push(`${changes.fieldsAdded.length} field(s) added`);
|
|
156
|
+
}
|
|
157
|
+
if (changes.typeChanges.length > 0) {
|
|
158
|
+
parts.push(`${changes.typeChanges.length} type change(s)`);
|
|
159
|
+
}
|
|
160
|
+
if (changes.newRequired.length > 0) {
|
|
161
|
+
parts.push(`${changes.newRequired.length} field(s) now required`);
|
|
162
|
+
}
|
|
163
|
+
if (changes.newOptional.length > 0) {
|
|
164
|
+
parts.push(`${changes.newOptional.length} field(s) now optional`);
|
|
165
|
+
}
|
|
166
|
+
if (parts.length === 0) {
|
|
167
|
+
return 'No schema changes';
|
|
168
|
+
}
|
|
169
|
+
return parts.join(', ');
|
|
170
|
+
}
|
|
171
|
+
/**
|
|
172
|
+
* Create an empty diff result.
|
|
173
|
+
*/
|
|
174
|
+
function createEmptyDiff() {
|
|
175
|
+
return {
|
|
176
|
+
structureChanged: false,
|
|
177
|
+
fieldsAdded: [],
|
|
178
|
+
fieldsRemoved: [],
|
|
179
|
+
typeChanges: [],
|
|
180
|
+
newRequired: [],
|
|
181
|
+
newOptional: [],
|
|
182
|
+
backwardCompatible: true,
|
|
183
|
+
isBreaking: false,
|
|
184
|
+
summary: 'No schema changes',
|
|
185
|
+
};
|
|
186
|
+
}
|
|
187
|
+
/**
|
|
188
|
+
* Build response schema evolution from multiple samples.
|
|
189
|
+
*
|
|
190
|
+
* @param schemas - Array of inferred schemas from samples
|
|
191
|
+
* @returns Schema evolution record
|
|
192
|
+
*/
|
|
193
|
+
export function buildSchemaEvolution(schemas) {
|
|
194
|
+
if (schemas.length === 0) {
|
|
195
|
+
return {
|
|
196
|
+
currentHash: 'empty',
|
|
197
|
+
history: [],
|
|
198
|
+
isStable: true,
|
|
199
|
+
stabilityConfidence: 0,
|
|
200
|
+
inconsistentFields: [],
|
|
201
|
+
sampleCount: 0,
|
|
202
|
+
};
|
|
203
|
+
}
|
|
204
|
+
// Track field presence across samples
|
|
205
|
+
const fieldPresence = new Map();
|
|
206
|
+
const fieldTypes = new Map();
|
|
207
|
+
for (const schema of schemas) {
|
|
208
|
+
if (schema.properties) {
|
|
209
|
+
for (const [field, propSchema] of Object.entries(schema.properties)) {
|
|
210
|
+
fieldPresence.set(field, (fieldPresence.get(field) ?? 0) + 1);
|
|
211
|
+
if (!fieldTypes.has(field)) {
|
|
212
|
+
fieldTypes.set(field, new Set());
|
|
213
|
+
}
|
|
214
|
+
fieldTypes.get(field).add(propSchema.type);
|
|
215
|
+
}
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
// Find inconsistent fields (not present in all samples or type varies)
|
|
219
|
+
const inconsistentFields = [];
|
|
220
|
+
for (const [field, count] of fieldPresence) {
|
|
221
|
+
if (count < schemas.length) {
|
|
222
|
+
inconsistentFields.push(field);
|
|
223
|
+
}
|
|
224
|
+
else if ((fieldTypes.get(field)?.size ?? 0) > 1) {
|
|
225
|
+
inconsistentFields.push(field);
|
|
226
|
+
}
|
|
227
|
+
}
|
|
228
|
+
// Calculate stability
|
|
229
|
+
const totalFields = fieldPresence.size;
|
|
230
|
+
const isStable = inconsistentFields.length === 0;
|
|
231
|
+
// Confidence based on consistency ratio and sample count
|
|
232
|
+
let stabilityConfidence = isStable
|
|
233
|
+
? 1
|
|
234
|
+
: 1 - (inconsistentFields.length / Math.max(1, totalFields));
|
|
235
|
+
// Adjust confidence based on sample count
|
|
236
|
+
// More samples = higher confidence in stability assessment
|
|
237
|
+
const sampleCountFactor = Math.min(1, schemas.length / SCHEMA_EVOLUTION.HIGH_CONFIDENCE_MIN_SAMPLES);
|
|
238
|
+
stabilityConfidence = stabilityConfidence * sampleCountFactor;
|
|
239
|
+
// Build history (most recent schema)
|
|
240
|
+
const currentSchema = schemas[schemas.length - 1];
|
|
241
|
+
const currentHash = computeInferredSchemaHash(currentSchema);
|
|
242
|
+
const history = [{
|
|
243
|
+
hash: currentHash,
|
|
244
|
+
schema: currentSchema,
|
|
245
|
+
observedAt: new Date(),
|
|
246
|
+
sampleCount: schemas.length,
|
|
247
|
+
}];
|
|
248
|
+
return {
|
|
249
|
+
currentHash,
|
|
250
|
+
history,
|
|
251
|
+
isStable,
|
|
252
|
+
stabilityConfidence: Math.round(stabilityConfidence * 100) / 100,
|
|
253
|
+
inconsistentFields: inconsistentFields.sort(),
|
|
254
|
+
sampleCount: schemas.length,
|
|
255
|
+
};
|
|
256
|
+
}
|
|
257
|
+
/**
|
|
258
|
+
* Compare schema evolution records between baselines.
|
|
259
|
+
*
|
|
260
|
+
* @param previous - Previous schema evolution
|
|
261
|
+
* @param current - Current schema evolution
|
|
262
|
+
* @returns Evolution comparison result
|
|
263
|
+
*/
|
|
264
|
+
export function compareSchemaEvolution(previous, current) {
|
|
265
|
+
// Handle missing evolution records
|
|
266
|
+
if (!previous && !current) {
|
|
267
|
+
return createEmptyDiff();
|
|
268
|
+
}
|
|
269
|
+
if (!previous) {
|
|
270
|
+
return {
|
|
271
|
+
...createEmptyDiff(),
|
|
272
|
+
structureChanged: (current?.inconsistentFields.length ?? 0) > 0 ||
|
|
273
|
+
current?.currentHash !== 'empty',
|
|
274
|
+
summary: current?.isStable
|
|
275
|
+
? 'Schema tracking established (stable)'
|
|
276
|
+
: `Schema tracking established (${current?.inconsistentFields.length ?? 0} inconsistent field(s))`,
|
|
277
|
+
};
|
|
278
|
+
}
|
|
279
|
+
if (!current) {
|
|
280
|
+
return {
|
|
281
|
+
...createEmptyDiff(),
|
|
282
|
+
structureChanged: true,
|
|
283
|
+
isBreaking: true,
|
|
284
|
+
backwardCompatible: false,
|
|
285
|
+
summary: 'Schema evolution data removed',
|
|
286
|
+
};
|
|
287
|
+
}
|
|
288
|
+
// Compare current schemas if available
|
|
289
|
+
const prevSchema = previous.history[0]?.schema;
|
|
290
|
+
const currSchema = current.history[0]?.schema;
|
|
291
|
+
if (prevSchema && currSchema) {
|
|
292
|
+
return compareInferredSchemas(prevSchema, currSchema);
|
|
293
|
+
}
|
|
294
|
+
// Compare hashes directly
|
|
295
|
+
if (previous.currentHash !== current.currentHash) {
|
|
296
|
+
return {
|
|
297
|
+
...createEmptyDiff(),
|
|
298
|
+
structureChanged: true,
|
|
299
|
+
summary: 'Schema hash changed',
|
|
300
|
+
};
|
|
301
|
+
}
|
|
302
|
+
// Check stability change
|
|
303
|
+
if (previous.isStable !== current.isStable) {
|
|
304
|
+
return {
|
|
305
|
+
...createEmptyDiff(),
|
|
306
|
+
structureChanged: false,
|
|
307
|
+
summary: current.isStable
|
|
308
|
+
? 'Schema stabilized'
|
|
309
|
+
: 'Schema became unstable',
|
|
310
|
+
};
|
|
311
|
+
}
|
|
312
|
+
return createEmptyDiff();
|
|
313
|
+
}
|
|
314
|
+
/**
|
|
315
|
+
* Format schema evolution for display.
|
|
316
|
+
*
|
|
317
|
+
* @param evolution - Schema evolution record
|
|
318
|
+
* @returns Formatted string representation
|
|
319
|
+
*/
|
|
320
|
+
export function formatSchemaEvolution(evolution) {
|
|
321
|
+
const lines = [];
|
|
322
|
+
const stabilityIcon = evolution.isStable ? '✓' : '⚠';
|
|
323
|
+
const confidencePercent = Math.round(evolution.stabilityConfidence * 100);
|
|
324
|
+
lines.push(`${stabilityIcon} Schema ${evolution.isStable ? 'Stable' : 'Unstable'} (${confidencePercent}% confidence)`);
|
|
325
|
+
if (evolution.sampleCount > 0) {
|
|
326
|
+
lines.push(` Samples: ${evolution.sampleCount}`);
|
|
327
|
+
lines.push(` Hash: ${evolution.currentHash}`);
|
|
328
|
+
}
|
|
329
|
+
if (evolution.inconsistentFields.length > 0) {
|
|
330
|
+
const fieldsDisplay = evolution.inconsistentFields.length <= 3
|
|
331
|
+
? evolution.inconsistentFields.join(', ')
|
|
332
|
+
: `${evolution.inconsistentFields.slice(0, 3).join(', ')} +${evolution.inconsistentFields.length - 3} more`;
|
|
333
|
+
lines.push(` Inconsistent fields: ${fieldsDisplay}`);
|
|
334
|
+
}
|
|
335
|
+
return lines.join('\n');
|
|
336
|
+
}
|
|
337
|
+
/**
|
|
338
|
+
* Format schema evolution diff for display.
|
|
339
|
+
*
|
|
340
|
+
* @param diff - Schema evolution diff
|
|
341
|
+
* @param useColors - Whether to use ANSI colors
|
|
342
|
+
* @returns Formatted string representation
|
|
343
|
+
*/
|
|
344
|
+
export function formatSchemaEvolutionDiff(diff, useColors = true) {
|
|
345
|
+
const lines = [];
|
|
346
|
+
const { red, green, yellow } = useColors ? colors : noColors;
|
|
347
|
+
if (!diff.structureChanged) {
|
|
348
|
+
return [];
|
|
349
|
+
}
|
|
350
|
+
if (diff.fieldsRemoved.length > 0) {
|
|
351
|
+
lines.push(red(` ${diff.fieldsRemoved.length} field(s) removed: ${diff.fieldsRemoved.join(', ')}`));
|
|
352
|
+
}
|
|
353
|
+
if (diff.fieldsAdded.length > 0) {
|
|
354
|
+
lines.push(green(` ${diff.fieldsAdded.length} field(s) added: ${diff.fieldsAdded.join(', ')}`));
|
|
355
|
+
}
|
|
356
|
+
for (const tc of diff.typeChanges) {
|
|
357
|
+
const changeColor = tc.backwardCompatible ? yellow : red;
|
|
358
|
+
lines.push(changeColor(` Type change: ${tc.field}: ${tc.previousType} → ${tc.currentType}`));
|
|
359
|
+
}
|
|
360
|
+
if (diff.newRequired.length > 0) {
|
|
361
|
+
lines.push(red(` Now required: ${diff.newRequired.join(', ')}`));
|
|
362
|
+
}
|
|
363
|
+
if (diff.newOptional.length > 0) {
|
|
364
|
+
lines.push(green(` Now optional: ${diff.newOptional.join(', ')}`));
|
|
365
|
+
}
|
|
366
|
+
return lines;
|
|
367
|
+
}
|
|
368
|
+
/**
|
|
369
|
+
* Determine if schema evolution indicates breaking changes.
|
|
370
|
+
*
|
|
371
|
+
* @param evolution - Schema evolution record
|
|
372
|
+
* @param threshold - Confidence threshold for stability
|
|
373
|
+
* @returns Whether the schema evolution indicates issues
|
|
374
|
+
*/
|
|
375
|
+
export function hasSchemaEvolutionIssues(evolution, threshold = SCHEMA_EVOLUTION.STABILITY_THRESHOLD) {
|
|
376
|
+
// Unstable schema with high sample count is concerning
|
|
377
|
+
if (!evolution.isStable && evolution.sampleCount >= SCHEMA_EVOLUTION.MIN_SAMPLES_FOR_STABILITY) {
|
|
378
|
+
return true;
|
|
379
|
+
}
|
|
380
|
+
// Low stability confidence with enough samples
|
|
381
|
+
if (evolution.stabilityConfidence < threshold &&
|
|
382
|
+
evolution.sampleCount >= SCHEMA_EVOLUTION.MIN_SAMPLES_FOR_STABILITY) {
|
|
383
|
+
return true;
|
|
384
|
+
}
|
|
385
|
+
return false;
|
|
386
|
+
}
|
|
387
|
+
/**
|
|
388
|
+
* Get schema evolution stability grade.
|
|
389
|
+
*
|
|
390
|
+
* @param evolution - Schema evolution record
|
|
391
|
+
* @returns Grade from A-F
|
|
392
|
+
*/
|
|
393
|
+
export function getSchemaStabilityGrade(evolution) {
|
|
394
|
+
if (evolution.sampleCount < SCHEMA_EVOLUTION.MIN_SAMPLES_FOR_STABILITY) {
|
|
395
|
+
return 'N/A';
|
|
396
|
+
}
|
|
397
|
+
const confidence = evolution.stabilityConfidence;
|
|
398
|
+
const { A, B, C, D } = SCHEMA_EVOLUTION.GRADE_THRESHOLDS;
|
|
399
|
+
if (evolution.isStable && confidence >= A)
|
|
400
|
+
return 'A';
|
|
401
|
+
if (confidence >= B)
|
|
402
|
+
return 'B';
|
|
403
|
+
if (confidence >= C)
|
|
404
|
+
return 'C';
|
|
405
|
+
if (confidence >= D)
|
|
406
|
+
return 'D';
|
|
407
|
+
return 'F';
|
|
408
|
+
}
|
|
409
|
+
// Color utilities
|
|
410
|
+
const colors = {
|
|
411
|
+
red: (s) => `\x1b[31m${s}\x1b[0m`,
|
|
412
|
+
green: (s) => `\x1b[32m${s}\x1b[0m`,
|
|
413
|
+
yellow: (s) => `\x1b[33m${s}\x1b[0m`,
|
|
414
|
+
};
|
|
415
|
+
const noColors = {
|
|
416
|
+
red: (s) => s,
|
|
417
|
+
green: (s) => s,
|
|
418
|
+
yellow: (s) => s,
|
|
419
|
+
};
|
|
420
|
+
//# sourceMappingURL=response-schema-tracker.js.map
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Regression Risk Scorer.
|
|
3
|
+
*
|
|
4
|
+
* Calculates weighted risk scores for detected changes to help prioritize fixes.
|
|
5
|
+
* Considers multiple factors: breaking changes, tool importance, error rates,
|
|
6
|
+
* performance regressions, and security posture.
|
|
7
|
+
*/
|
|
8
|
+
import type { BehavioralDiff } from './types.js';
|
|
9
|
+
/**
|
|
10
|
+
* A single risk factor contributing to the overall score.
|
|
11
|
+
*/
|
|
12
|
+
export interface RiskFactor {
|
|
13
|
+
/** Name of the risk factor */
|
|
14
|
+
name: string;
|
|
15
|
+
/** Weight in overall calculation (0-1) */
|
|
16
|
+
weight: number;
|
|
17
|
+
/** Raw score (0-100) */
|
|
18
|
+
score: number;
|
|
19
|
+
/** Weighted contribution to overall score */
|
|
20
|
+
weightedScore: number;
|
|
21
|
+
/** Details about this factor */
|
|
22
|
+
details: string;
|
|
23
|
+
}
|
|
24
|
+
/**
|
|
25
|
+
* Complete regression risk score.
|
|
26
|
+
*/
|
|
27
|
+
export interface RegressionRiskScore {
|
|
28
|
+
/** Overall risk score (0-100) */
|
|
29
|
+
score: number;
|
|
30
|
+
/** Risk level classification */
|
|
31
|
+
level: 'critical' | 'high' | 'medium' | 'low' | 'info';
|
|
32
|
+
/** Individual risk factors */
|
|
33
|
+
factors: RiskFactor[];
|
|
34
|
+
/** Human-readable recommendation */
|
|
35
|
+
recommendation: string;
|
|
36
|
+
/** Breakdown of changes by severity */
|
|
37
|
+
changeSummary: {
|
|
38
|
+
breaking: number;
|
|
39
|
+
warning: number;
|
|
40
|
+
info: number;
|
|
41
|
+
toolsRemoved: number;
|
|
42
|
+
toolsAdded: number;
|
|
43
|
+
toolsModified: number;
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
/**
|
|
47
|
+
* Calculate regression risk score from a behavioral diff.
|
|
48
|
+
*/
|
|
49
|
+
export declare function calculateRiskScore(diff: BehavioralDiff): RegressionRiskScore;
|
|
50
|
+
/**
|
|
51
|
+
* Generate markdown report for risk score.
|
|
52
|
+
*/
|
|
53
|
+
export declare function generateRiskScoreMarkdown(riskScore: RegressionRiskScore): string;
|
|
54
|
+
//# sourceMappingURL=risk-scorer.d.ts.map
|