@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.
Files changed (403) hide show
  1. package/CHANGELOG.md +291 -0
  2. package/LICENSE +21 -0
  3. package/README.md +739 -0
  4. package/dist/auth/credentials.d.ts +64 -0
  5. package/dist/auth/credentials.js +218 -0
  6. package/dist/auth/index.d.ts +6 -0
  7. package/dist/auth/index.js +6 -0
  8. package/dist/auth/keychain.d.ts +64 -0
  9. package/dist/auth/keychain.js +268 -0
  10. package/dist/baseline/ab-testing.d.ts +80 -0
  11. package/dist/baseline/ab-testing.js +236 -0
  12. package/dist/baseline/ai-compatibility-scorer.d.ts +95 -0
  13. package/dist/baseline/ai-compatibility-scorer.js +606 -0
  14. package/dist/baseline/calibration.d.ts +77 -0
  15. package/dist/baseline/calibration.js +136 -0
  16. package/dist/baseline/category-matching.d.ts +85 -0
  17. package/dist/baseline/category-matching.js +289 -0
  18. package/dist/baseline/change-impact-analyzer.d.ts +98 -0
  19. package/dist/baseline/change-impact-analyzer.js +592 -0
  20. package/dist/baseline/comparator.d.ts +64 -0
  21. package/dist/baseline/comparator.js +916 -0
  22. package/dist/baseline/confidence.d.ts +55 -0
  23. package/dist/baseline/confidence.js +122 -0
  24. package/dist/baseline/converter.d.ts +61 -0
  25. package/dist/baseline/converter.js +585 -0
  26. package/dist/baseline/dependency-analyzer.d.ts +89 -0
  27. package/dist/baseline/dependency-analyzer.js +567 -0
  28. package/dist/baseline/deprecation-tracker.d.ts +133 -0
  29. package/dist/baseline/deprecation-tracker.js +322 -0
  30. package/dist/baseline/diff.d.ts +55 -0
  31. package/dist/baseline/diff.js +1584 -0
  32. package/dist/baseline/documentation-scorer.d.ts +205 -0
  33. package/dist/baseline/documentation-scorer.js +466 -0
  34. package/dist/baseline/embeddings.d.ts +118 -0
  35. package/dist/baseline/embeddings.js +251 -0
  36. package/dist/baseline/error-analyzer.d.ts +198 -0
  37. package/dist/baseline/error-analyzer.js +721 -0
  38. package/dist/baseline/evaluation/evaluator.d.ts +42 -0
  39. package/dist/baseline/evaluation/evaluator.js +323 -0
  40. package/dist/baseline/evaluation/expanded-dataset.d.ts +45 -0
  41. package/dist/baseline/evaluation/expanded-dataset.js +1164 -0
  42. package/dist/baseline/evaluation/golden-dataset.d.ts +58 -0
  43. package/dist/baseline/evaluation/golden-dataset.js +717 -0
  44. package/dist/baseline/evaluation/index.d.ts +15 -0
  45. package/dist/baseline/evaluation/index.js +15 -0
  46. package/dist/baseline/evaluation/types.d.ts +186 -0
  47. package/dist/baseline/evaluation/types.js +8 -0
  48. package/dist/baseline/external-dependency-detector.d.ts +181 -0
  49. package/dist/baseline/external-dependency-detector.js +524 -0
  50. package/dist/baseline/golden-output.d.ts +162 -0
  51. package/dist/baseline/golden-output.js +636 -0
  52. package/dist/baseline/health-scorer.d.ts +174 -0
  53. package/dist/baseline/health-scorer.js +451 -0
  54. package/dist/baseline/incremental-checker.d.ts +97 -0
  55. package/dist/baseline/incremental-checker.js +174 -0
  56. package/dist/baseline/index.d.ts +31 -0
  57. package/dist/baseline/index.js +42 -0
  58. package/dist/baseline/migration-generator.d.ts +137 -0
  59. package/dist/baseline/migration-generator.js +554 -0
  60. package/dist/baseline/migrations.d.ts +60 -0
  61. package/dist/baseline/migrations.js +197 -0
  62. package/dist/baseline/performance-tracker.d.ts +214 -0
  63. package/dist/baseline/performance-tracker.js +577 -0
  64. package/dist/baseline/pr-comment-generator.d.ts +117 -0
  65. package/dist/baseline/pr-comment-generator.js +546 -0
  66. package/dist/baseline/response-fingerprint.d.ts +127 -0
  67. package/dist/baseline/response-fingerprint.js +728 -0
  68. package/dist/baseline/response-schema-tracker.d.ts +129 -0
  69. package/dist/baseline/response-schema-tracker.js +420 -0
  70. package/dist/baseline/risk-scorer.d.ts +54 -0
  71. package/dist/baseline/risk-scorer.js +434 -0
  72. package/dist/baseline/saver.d.ts +89 -0
  73. package/dist/baseline/saver.js +554 -0
  74. package/dist/baseline/scenario-generator.d.ts +151 -0
  75. package/dist/baseline/scenario-generator.js +905 -0
  76. package/dist/baseline/schema-compare.d.ts +86 -0
  77. package/dist/baseline/schema-compare.js +557 -0
  78. package/dist/baseline/schema-evolution.d.ts +189 -0
  79. package/dist/baseline/schema-evolution.js +467 -0
  80. package/dist/baseline/semantic.d.ts +203 -0
  81. package/dist/baseline/semantic.js +908 -0
  82. package/dist/baseline/synonyms.d.ts +60 -0
  83. package/dist/baseline/synonyms.js +386 -0
  84. package/dist/baseline/telemetry.d.ts +165 -0
  85. package/dist/baseline/telemetry.js +294 -0
  86. package/dist/baseline/test-pruner.d.ts +120 -0
  87. package/dist/baseline/test-pruner.js +387 -0
  88. package/dist/baseline/types.d.ts +449 -0
  89. package/dist/baseline/types.js +5 -0
  90. package/dist/baseline/version.d.ts +138 -0
  91. package/dist/baseline/version.js +206 -0
  92. package/dist/cache/index.d.ts +5 -0
  93. package/dist/cache/index.js +5 -0
  94. package/dist/cache/response-cache.d.ts +151 -0
  95. package/dist/cache/response-cache.js +287 -0
  96. package/dist/ci/index.d.ts +60 -0
  97. package/dist/ci/index.js +342 -0
  98. package/dist/cli/commands/auth.d.ts +12 -0
  99. package/dist/cli/commands/auth.js +352 -0
  100. package/dist/cli/commands/badge.d.ts +3 -0
  101. package/dist/cli/commands/badge.js +74 -0
  102. package/dist/cli/commands/baseline-accept.d.ts +15 -0
  103. package/dist/cli/commands/baseline-accept.js +178 -0
  104. package/dist/cli/commands/baseline-migrate.d.ts +12 -0
  105. package/dist/cli/commands/baseline-migrate.js +164 -0
  106. package/dist/cli/commands/baseline.d.ts +14 -0
  107. package/dist/cli/commands/baseline.js +449 -0
  108. package/dist/cli/commands/beta.d.ts +10 -0
  109. package/dist/cli/commands/beta.js +231 -0
  110. package/dist/cli/commands/check.d.ts +11 -0
  111. package/dist/cli/commands/check.js +820 -0
  112. package/dist/cli/commands/cloud/badge.d.ts +3 -0
  113. package/dist/cli/commands/cloud/badge.js +74 -0
  114. package/dist/cli/commands/cloud/diff.d.ts +6 -0
  115. package/dist/cli/commands/cloud/diff.js +79 -0
  116. package/dist/cli/commands/cloud/history.d.ts +6 -0
  117. package/dist/cli/commands/cloud/history.js +102 -0
  118. package/dist/cli/commands/cloud/link.d.ts +9 -0
  119. package/dist/cli/commands/cloud/link.js +119 -0
  120. package/dist/cli/commands/cloud/login.d.ts +7 -0
  121. package/dist/cli/commands/cloud/login.js +499 -0
  122. package/dist/cli/commands/cloud/projects.d.ts +6 -0
  123. package/dist/cli/commands/cloud/projects.js +44 -0
  124. package/dist/cli/commands/cloud/shared.d.ts +7 -0
  125. package/dist/cli/commands/cloud/shared.js +42 -0
  126. package/dist/cli/commands/cloud/teams.d.ts +8 -0
  127. package/dist/cli/commands/cloud/teams.js +169 -0
  128. package/dist/cli/commands/cloud/upload.d.ts +8 -0
  129. package/dist/cli/commands/cloud/upload.js +181 -0
  130. package/dist/cli/commands/contract.d.ts +11 -0
  131. package/dist/cli/commands/contract.js +280 -0
  132. package/dist/cli/commands/discover.d.ts +3 -0
  133. package/dist/cli/commands/discover.js +82 -0
  134. package/dist/cli/commands/eval.d.ts +9 -0
  135. package/dist/cli/commands/eval.js +187 -0
  136. package/dist/cli/commands/explore.d.ts +11 -0
  137. package/dist/cli/commands/explore.js +437 -0
  138. package/dist/cli/commands/feedback.d.ts +9 -0
  139. package/dist/cli/commands/feedback.js +174 -0
  140. package/dist/cli/commands/golden.d.ts +12 -0
  141. package/dist/cli/commands/golden.js +407 -0
  142. package/dist/cli/commands/history.d.ts +10 -0
  143. package/dist/cli/commands/history.js +202 -0
  144. package/dist/cli/commands/init.d.ts +9 -0
  145. package/dist/cli/commands/init.js +219 -0
  146. package/dist/cli/commands/interview.d.ts +3 -0
  147. package/dist/cli/commands/interview.js +903 -0
  148. package/dist/cli/commands/link.d.ts +10 -0
  149. package/dist/cli/commands/link.js +169 -0
  150. package/dist/cli/commands/login.d.ts +7 -0
  151. package/dist/cli/commands/login.js +499 -0
  152. package/dist/cli/commands/preset.d.ts +33 -0
  153. package/dist/cli/commands/preset.js +297 -0
  154. package/dist/cli/commands/profile.d.ts +33 -0
  155. package/dist/cli/commands/profile.js +286 -0
  156. package/dist/cli/commands/registry.d.ts +11 -0
  157. package/dist/cli/commands/registry.js +146 -0
  158. package/dist/cli/commands/shared.d.ts +79 -0
  159. package/dist/cli/commands/shared.js +196 -0
  160. package/dist/cli/commands/teams.d.ts +8 -0
  161. package/dist/cli/commands/teams.js +169 -0
  162. package/dist/cli/commands/test.d.ts +9 -0
  163. package/dist/cli/commands/test.js +500 -0
  164. package/dist/cli/commands/upload.d.ts +8 -0
  165. package/dist/cli/commands/upload.js +223 -0
  166. package/dist/cli/commands/validate-config.d.ts +6 -0
  167. package/dist/cli/commands/validate-config.js +35 -0
  168. package/dist/cli/commands/verify.d.ts +11 -0
  169. package/dist/cli/commands/verify.js +283 -0
  170. package/dist/cli/commands/watch.d.ts +12 -0
  171. package/dist/cli/commands/watch.js +253 -0
  172. package/dist/cli/index.d.ts +3 -0
  173. package/dist/cli/index.js +178 -0
  174. package/dist/cli/interactive.d.ts +47 -0
  175. package/dist/cli/interactive.js +216 -0
  176. package/dist/cli/output/terminal-reporter.d.ts +19 -0
  177. package/dist/cli/output/terminal-reporter.js +104 -0
  178. package/dist/cli/output.d.ts +226 -0
  179. package/dist/cli/output.js +438 -0
  180. package/dist/cli/utils/env.d.ts +5 -0
  181. package/dist/cli/utils/env.js +14 -0
  182. package/dist/cli/utils/progress.d.ts +59 -0
  183. package/dist/cli/utils/progress.js +206 -0
  184. package/dist/cli/utils/server-context.d.ts +10 -0
  185. package/dist/cli/utils/server-context.js +36 -0
  186. package/dist/cloud/auth.d.ts +144 -0
  187. package/dist/cloud/auth.js +374 -0
  188. package/dist/cloud/client.d.ts +24 -0
  189. package/dist/cloud/client.js +65 -0
  190. package/dist/cloud/http-client.d.ts +38 -0
  191. package/dist/cloud/http-client.js +215 -0
  192. package/dist/cloud/index.d.ts +23 -0
  193. package/dist/cloud/index.js +25 -0
  194. package/dist/cloud/mock-client.d.ts +107 -0
  195. package/dist/cloud/mock-client.js +545 -0
  196. package/dist/cloud/types.d.ts +515 -0
  197. package/dist/cloud/types.js +15 -0
  198. package/dist/config/defaults.d.ts +160 -0
  199. package/dist/config/defaults.js +169 -0
  200. package/dist/config/loader.d.ts +24 -0
  201. package/dist/config/loader.js +122 -0
  202. package/dist/config/template.d.ts +42 -0
  203. package/dist/config/template.js +647 -0
  204. package/dist/config/validator.d.ts +2112 -0
  205. package/dist/config/validator.js +658 -0
  206. package/dist/constants/cloud.d.ts +107 -0
  207. package/dist/constants/cloud.js +110 -0
  208. package/dist/constants/core.d.ts +521 -0
  209. package/dist/constants/core.js +556 -0
  210. package/dist/constants/testing.d.ts +1283 -0
  211. package/dist/constants/testing.js +1568 -0
  212. package/dist/constants.d.ts +10 -0
  213. package/dist/constants.js +10 -0
  214. package/dist/contract/index.d.ts +6 -0
  215. package/dist/contract/index.js +5 -0
  216. package/dist/contract/validator.d.ts +177 -0
  217. package/dist/contract/validator.js +574 -0
  218. package/dist/cost/index.d.ts +6 -0
  219. package/dist/cost/index.js +5 -0
  220. package/dist/cost/tracker.d.ts +134 -0
  221. package/dist/cost/tracker.js +313 -0
  222. package/dist/discovery/discovery.d.ts +16 -0
  223. package/dist/discovery/discovery.js +173 -0
  224. package/dist/discovery/types.d.ts +51 -0
  225. package/dist/discovery/types.js +2 -0
  226. package/dist/docs/agents.d.ts +3 -0
  227. package/dist/docs/agents.js +995 -0
  228. package/dist/docs/contract.d.ts +51 -0
  229. package/dist/docs/contract.js +1681 -0
  230. package/dist/docs/generator.d.ts +4 -0
  231. package/dist/docs/generator.js +4 -0
  232. package/dist/docs/html-reporter.d.ts +9 -0
  233. package/dist/docs/html-reporter.js +757 -0
  234. package/dist/docs/index.d.ts +10 -0
  235. package/dist/docs/index.js +11 -0
  236. package/dist/docs/junit-reporter.d.ts +18 -0
  237. package/dist/docs/junit-reporter.js +210 -0
  238. package/dist/docs/report.d.ts +14 -0
  239. package/dist/docs/report.js +44 -0
  240. package/dist/docs/sarif-reporter.d.ts +19 -0
  241. package/dist/docs/sarif-reporter.js +335 -0
  242. package/dist/docs/shared.d.ts +35 -0
  243. package/dist/docs/shared.js +162 -0
  244. package/dist/docs/templates.d.ts +12 -0
  245. package/dist/docs/templates.js +76 -0
  246. package/dist/errors/index.d.ts +6 -0
  247. package/dist/errors/index.js +6 -0
  248. package/dist/errors/retry.d.ts +92 -0
  249. package/dist/errors/retry.js +323 -0
  250. package/dist/errors/types.d.ts +321 -0
  251. package/dist/errors/types.js +584 -0
  252. package/dist/index.d.ts +32 -0
  253. package/dist/index.js +32 -0
  254. package/dist/interview/dependency-resolver.d.ts +11 -0
  255. package/dist/interview/dependency-resolver.js +32 -0
  256. package/dist/interview/interviewer.d.ts +232 -0
  257. package/dist/interview/interviewer.js +1939 -0
  258. package/dist/interview/mock-response-generator.d.ts +7 -0
  259. package/dist/interview/mock-response-generator.js +102 -0
  260. package/dist/interview/orchestrator.d.ts +237 -0
  261. package/dist/interview/orchestrator.js +1296 -0
  262. package/dist/interview/rate-limiter.d.ts +15 -0
  263. package/dist/interview/rate-limiter.js +55 -0
  264. package/dist/interview/response-validator.d.ts +10 -0
  265. package/dist/interview/response-validator.js +132 -0
  266. package/dist/interview/schema-inferrer.d.ts +8 -0
  267. package/dist/interview/schema-inferrer.js +71 -0
  268. package/dist/interview/schema-test-generator.d.ts +71 -0
  269. package/dist/interview/schema-test-generator.js +834 -0
  270. package/dist/interview/smart-value-generator.d.ts +155 -0
  271. package/dist/interview/smart-value-generator.js +554 -0
  272. package/dist/interview/stateful-test-runner.d.ts +19 -0
  273. package/dist/interview/stateful-test-runner.js +106 -0
  274. package/dist/interview/types.d.ts +561 -0
  275. package/dist/interview/types.js +2 -0
  276. package/dist/llm/anthropic.d.ts +41 -0
  277. package/dist/llm/anthropic.js +355 -0
  278. package/dist/llm/client.d.ts +123 -0
  279. package/dist/llm/client.js +42 -0
  280. package/dist/llm/factory.d.ts +38 -0
  281. package/dist/llm/factory.js +145 -0
  282. package/dist/llm/fallback.d.ts +140 -0
  283. package/dist/llm/fallback.js +379 -0
  284. package/dist/llm/index.d.ts +18 -0
  285. package/dist/llm/index.js +15 -0
  286. package/dist/llm/ollama.d.ts +37 -0
  287. package/dist/llm/ollama.js +330 -0
  288. package/dist/llm/openai.d.ts +25 -0
  289. package/dist/llm/openai.js +320 -0
  290. package/dist/llm/token-budget.d.ts +161 -0
  291. package/dist/llm/token-budget.js +395 -0
  292. package/dist/logging/logger.d.ts +70 -0
  293. package/dist/logging/logger.js +130 -0
  294. package/dist/metrics/collector.d.ts +106 -0
  295. package/dist/metrics/collector.js +547 -0
  296. package/dist/metrics/index.d.ts +7 -0
  297. package/dist/metrics/index.js +7 -0
  298. package/dist/metrics/prometheus.d.ts +20 -0
  299. package/dist/metrics/prometheus.js +241 -0
  300. package/dist/metrics/types.d.ts +209 -0
  301. package/dist/metrics/types.js +5 -0
  302. package/dist/persona/builtins.d.ts +54 -0
  303. package/dist/persona/builtins.js +219 -0
  304. package/dist/persona/index.d.ts +8 -0
  305. package/dist/persona/index.js +8 -0
  306. package/dist/persona/loader.d.ts +30 -0
  307. package/dist/persona/loader.js +190 -0
  308. package/dist/persona/types.d.ts +144 -0
  309. package/dist/persona/types.js +5 -0
  310. package/dist/persona/validation.d.ts +94 -0
  311. package/dist/persona/validation.js +332 -0
  312. package/dist/prompts/index.d.ts +5 -0
  313. package/dist/prompts/index.js +5 -0
  314. package/dist/prompts/templates.d.ts +180 -0
  315. package/dist/prompts/templates.js +431 -0
  316. package/dist/registry/client.d.ts +49 -0
  317. package/dist/registry/client.js +191 -0
  318. package/dist/registry/index.d.ts +7 -0
  319. package/dist/registry/index.js +6 -0
  320. package/dist/registry/types.d.ts +140 -0
  321. package/dist/registry/types.js +6 -0
  322. package/dist/scenarios/evaluator.d.ts +43 -0
  323. package/dist/scenarios/evaluator.js +206 -0
  324. package/dist/scenarios/index.d.ts +10 -0
  325. package/dist/scenarios/index.js +9 -0
  326. package/dist/scenarios/loader.d.ts +20 -0
  327. package/dist/scenarios/loader.js +285 -0
  328. package/dist/scenarios/types.d.ts +153 -0
  329. package/dist/scenarios/types.js +8 -0
  330. package/dist/security/index.d.ts +17 -0
  331. package/dist/security/index.js +18 -0
  332. package/dist/security/payloads.d.ts +61 -0
  333. package/dist/security/payloads.js +268 -0
  334. package/dist/security/security-tester.d.ts +42 -0
  335. package/dist/security/security-tester.js +582 -0
  336. package/dist/security/types.d.ts +166 -0
  337. package/dist/security/types.js +8 -0
  338. package/dist/transport/base-transport.d.ts +59 -0
  339. package/dist/transport/base-transport.js +38 -0
  340. package/dist/transport/http-transport.d.ts +67 -0
  341. package/dist/transport/http-transport.js +238 -0
  342. package/dist/transport/mcp-client.d.ts +141 -0
  343. package/dist/transport/mcp-client.js +496 -0
  344. package/dist/transport/sse-transport.d.ts +88 -0
  345. package/dist/transport/sse-transport.js +316 -0
  346. package/dist/transport/stdio-transport.d.ts +43 -0
  347. package/dist/transport/stdio-transport.js +238 -0
  348. package/dist/transport/types.d.ts +125 -0
  349. package/dist/transport/types.js +16 -0
  350. package/dist/utils/concurrency.d.ts +123 -0
  351. package/dist/utils/concurrency.js +213 -0
  352. package/dist/utils/formatters.d.ts +16 -0
  353. package/dist/utils/formatters.js +37 -0
  354. package/dist/utils/index.d.ts +8 -0
  355. package/dist/utils/index.js +8 -0
  356. package/dist/utils/jsonpath.d.ts +87 -0
  357. package/dist/utils/jsonpath.js +326 -0
  358. package/dist/utils/markdown.d.ts +113 -0
  359. package/dist/utils/markdown.js +265 -0
  360. package/dist/utils/network.d.ts +14 -0
  361. package/dist/utils/network.js +17 -0
  362. package/dist/utils/sanitize.d.ts +92 -0
  363. package/dist/utils/sanitize.js +191 -0
  364. package/dist/utils/semantic.d.ts +194 -0
  365. package/dist/utils/semantic.js +1051 -0
  366. package/dist/utils/smart-truncate.d.ts +94 -0
  367. package/dist/utils/smart-truncate.js +361 -0
  368. package/dist/utils/timeout.d.ts +153 -0
  369. package/dist/utils/timeout.js +205 -0
  370. package/dist/utils/yaml-parser.d.ts +58 -0
  371. package/dist/utils/yaml-parser.js +86 -0
  372. package/dist/validation/index.d.ts +32 -0
  373. package/dist/validation/index.js +32 -0
  374. package/dist/validation/semantic-test-generator.d.ts +50 -0
  375. package/dist/validation/semantic-test-generator.js +176 -0
  376. package/dist/validation/semantic-types.d.ts +66 -0
  377. package/dist/validation/semantic-types.js +94 -0
  378. package/dist/validation/semantic-validator.d.ts +38 -0
  379. package/dist/validation/semantic-validator.js +340 -0
  380. package/dist/verification/index.d.ts +6 -0
  381. package/dist/verification/index.js +5 -0
  382. package/dist/verification/types.d.ts +133 -0
  383. package/dist/verification/types.js +5 -0
  384. package/dist/verification/verifier.d.ts +30 -0
  385. package/dist/verification/verifier.js +309 -0
  386. package/dist/version.d.ts +19 -0
  387. package/dist/version.js +48 -0
  388. package/dist/workflow/auto-generator.d.ts +27 -0
  389. package/dist/workflow/auto-generator.js +513 -0
  390. package/dist/workflow/discovery.d.ts +40 -0
  391. package/dist/workflow/discovery.js +195 -0
  392. package/dist/workflow/executor.d.ts +82 -0
  393. package/dist/workflow/executor.js +611 -0
  394. package/dist/workflow/index.d.ts +10 -0
  395. package/dist/workflow/index.js +10 -0
  396. package/dist/workflow/loader.d.ts +24 -0
  397. package/dist/workflow/loader.js +194 -0
  398. package/dist/workflow/state-tracker.d.ts +98 -0
  399. package/dist/workflow/state-tracker.js +424 -0
  400. package/dist/workflow/types.d.ts +337 -0
  401. package/dist/workflow/types.js +5 -0
  402. package/package.json +94 -0
  403. package/schemas/bellwether-check.schema.json +651 -0
@@ -0,0 +1,352 @@
1
+ /**
2
+ * Auth command for managing LLM provider API keys.
3
+ *
4
+ * Provides secure storage via system keychain with fallback to file-based storage.
5
+ * Separate from the `login` command which handles Bellwether Cloud authentication.
6
+ */
7
+ import { Command } from 'commander';
8
+ import * as readline from 'readline';
9
+ import { DEFAULT_MODELS } from '../../llm/client.js';
10
+ import { getKeychainService } from '../../auth/keychain.js';
11
+ import { getAuthStatus } from '../../auth/credentials.js';
12
+ import { EXIT_CODES } from '../../constants.js';
13
+ import * as output from '../output.js';
14
+ /**
15
+ * Provider display names and info.
16
+ */
17
+ const PROVIDER_INFO = {
18
+ openai: {
19
+ name: 'OpenAI',
20
+ url: 'https://platform.openai.com/api-keys',
21
+ envVar: 'OPENAI_API_KEY',
22
+ },
23
+ anthropic: {
24
+ name: 'Anthropic',
25
+ url: 'https://console.anthropic.com/settings/keys',
26
+ envVar: 'ANTHROPIC_API_KEY',
27
+ },
28
+ };
29
+ /**
30
+ * Create a readline interface for prompts.
31
+ */
32
+ function createPrompt() {
33
+ return readline.createInterface({
34
+ input: process.stdin,
35
+ output: process.stdout,
36
+ });
37
+ }
38
+ /**
39
+ * Prompt user for input (hidden for passwords).
40
+ */
41
+ async function prompt(rl, question, hidden = false) {
42
+ return new Promise((resolve) => {
43
+ if (hidden && process.stdin.isTTY) {
44
+ // Hide input for sensitive data
45
+ const stdin = process.stdin;
46
+ const stdout = process.stdout;
47
+ stdout.write(question);
48
+ stdin.setRawMode(true);
49
+ stdin.resume();
50
+ stdin.setEncoding('utf8');
51
+ let input = '';
52
+ const onData = (char) => {
53
+ const charCode = char.charCodeAt(0);
54
+ if (charCode === 13 || charCode === 10) {
55
+ // Enter
56
+ stdin.setRawMode(false);
57
+ stdin.removeListener('data', onData);
58
+ stdout.write('\n');
59
+ resolve(input);
60
+ }
61
+ else if (charCode === 127 || charCode === 8) {
62
+ // Backspace
63
+ if (input.length > 0) {
64
+ input = input.slice(0, -1);
65
+ stdout.clearLine(0);
66
+ stdout.cursorTo(0);
67
+ stdout.write(question + '*'.repeat(input.length));
68
+ }
69
+ }
70
+ else if (charCode === 3) {
71
+ // Ctrl+C
72
+ process.exit(EXIT_CODES.CLEAN);
73
+ }
74
+ else if (charCode >= 32) {
75
+ // Printable character
76
+ input += char;
77
+ stdout.write('*');
78
+ }
79
+ };
80
+ stdin.on('data', onData);
81
+ }
82
+ else {
83
+ // Fallback for non-TTY
84
+ rl.question(question, resolve);
85
+ }
86
+ });
87
+ }
88
+ /**
89
+ * Prompt user to select from a list.
90
+ */
91
+ async function promptSelect(rl, question, options) {
92
+ output.info(question);
93
+ options.forEach((opt, i) => {
94
+ output.info(` ${i + 1}. ${opt.label}`);
95
+ });
96
+ const answer = await prompt(rl, `Enter choice (1-${options.length}): `);
97
+ const index = parseInt(answer, 10) - 1;
98
+ if (index >= 0 && index < options.length) {
99
+ return options[index].value;
100
+ }
101
+ output.info('Invalid choice. Please try again.\n');
102
+ return promptSelect(rl, question, options);
103
+ }
104
+ /**
105
+ * Validate API key format.
106
+ */
107
+ function validateApiKey(provider, key) {
108
+ if (!key || key.trim().length === 0) {
109
+ return { valid: false, error: 'API key cannot be empty' };
110
+ }
111
+ if (provider === 'openai') {
112
+ // OpenAI keys start with sk-
113
+ if (!key.startsWith('sk-')) {
114
+ return { valid: false, error: 'OpenAI API keys should start with "sk-"' };
115
+ }
116
+ if (key.length < 20) {
117
+ return { valid: false, error: 'API key appears too short' };
118
+ }
119
+ }
120
+ if (provider === 'anthropic') {
121
+ // Anthropic keys start with sk-ant-
122
+ if (!key.startsWith('sk-ant-')) {
123
+ return { valid: false, error: 'Anthropic API keys should start with "sk-ant-"' };
124
+ }
125
+ if (key.length < 20) {
126
+ return { valid: false, error: 'API key appears too short' };
127
+ }
128
+ }
129
+ return { valid: true };
130
+ }
131
+ /**
132
+ * Interactive auth setup.
133
+ */
134
+ async function interactiveSetup() {
135
+ const rl = createPrompt();
136
+ output.info('Bellwether Authentication Setup');
137
+ output.info('================================\n');
138
+ // Check current status
139
+ const status = await getAuthStatus();
140
+ const configuredProviders = status.filter(s => s.provider !== 'ollama' && s.configured);
141
+ if (configuredProviders.length > 0) {
142
+ output.info('Currently configured:');
143
+ for (const s of configuredProviders) {
144
+ const source = s.source === 'keychain' ? 'keychain' :
145
+ s.source === 'env' ? `env (${s.envVar})` : s.source;
146
+ output.info(` - ${PROVIDER_INFO[s.provider]?.name ?? s.provider}: ${source}`);
147
+ }
148
+ output.newline();
149
+ }
150
+ // Select provider
151
+ const provider = await promptSelect(rl, 'Which LLM provider would you like to configure?', [
152
+ { value: 'anthropic', label: 'Anthropic Claude (recommended)' },
153
+ { value: 'openai', label: 'OpenAI' },
154
+ ]);
155
+ const info = PROVIDER_INFO[provider];
156
+ output.info(`\nGet your ${info.name} API key from:`);
157
+ output.info(` ${info.url}\n`);
158
+ // Get API key
159
+ const apiKey = await prompt(rl, `Enter your ${info.name} API key: `, true);
160
+ // Validate
161
+ const validation = validateApiKey(provider, apiKey);
162
+ if (!validation.valid) {
163
+ output.error(`\nError: ${validation.error}`);
164
+ rl.close();
165
+ process.exit(EXIT_CODES.ERROR);
166
+ }
167
+ // Check keychain availability
168
+ const keychain = getKeychainService();
169
+ const hasSecureKeychain = await keychain.isSecureKeychainAvailable();
170
+ let storageChoice;
171
+ if (hasSecureKeychain) {
172
+ storageChoice = await promptSelect(rl, '\nWhere would you like to store the API key?', [
173
+ { value: 'keychain', label: 'System keychain (recommended - most secure)' },
174
+ { value: 'env', label: `Environment file (~/.bellwether/.env)` },
175
+ ]);
176
+ }
177
+ else {
178
+ output.info('\nNote: System keychain not available. Using file-based storage.');
179
+ storageChoice = 'env';
180
+ }
181
+ // Store the key
182
+ try {
183
+ if (storageChoice === 'keychain') {
184
+ await keychain.setApiKey(provider, apiKey);
185
+ output.success(`\n\u2713 API key stored in system keychain`);
186
+ }
187
+ else {
188
+ // Store in ~/.bellwether/.env
189
+ const fs = await import('fs');
190
+ const path = await import('path');
191
+ const os = await import('os');
192
+ const envDir = path.join(os.homedir(), '.bellwether');
193
+ const envPath = path.join(envDir, '.env');
194
+ if (!fs.existsSync(envDir)) {
195
+ fs.mkdirSync(envDir, { recursive: true, mode: 0o700 });
196
+ }
197
+ // Read existing .env or create new
198
+ let envContent = '';
199
+ if (fs.existsSync(envPath)) {
200
+ envContent = fs.readFileSync(envPath, 'utf-8');
201
+ }
202
+ // Update or add the key
203
+ const envVar = info.envVar;
204
+ const lines = envContent.split('\n').filter(line => !line.startsWith(`${envVar}=`));
205
+ lines.push(`${envVar}=${apiKey}`);
206
+ fs.writeFileSync(envPath, lines.filter(l => l).join('\n') + '\n', { mode: 0o600 });
207
+ output.success(`\n\u2713 API key stored in ~/.bellwether/.env`);
208
+ }
209
+ output.info(`\nYou're all set! Bellwether will now use ${info.name} for tests.`);
210
+ output.info(`\nDefault model: ${DEFAULT_MODELS[provider]}`);
211
+ output.info('\nTry it out:');
212
+ output.info(' bellwether explore npx @modelcontextprotocol/server-memory');
213
+ }
214
+ catch (error) {
215
+ output.error(`\nFailed to store API key: ${error instanceof Error ? error.message : error}`);
216
+ process.exit(EXIT_CODES.ERROR);
217
+ }
218
+ rl.close();
219
+ }
220
+ /**
221
+ * Show auth status.
222
+ */
223
+ async function showStatus() {
224
+ output.info('Bellwether Authentication Status');
225
+ output.info('=================================\n');
226
+ const status = await getAuthStatus();
227
+ for (const s of status) {
228
+ if (s.provider === 'ollama') {
229
+ output.info('Ollama:');
230
+ output.info(' Status: No API key required (local)');
231
+ output.info(' Model: qwen3:8b');
232
+ output.newline();
233
+ continue;
234
+ }
235
+ const info = PROVIDER_INFO[s.provider];
236
+ if (!info)
237
+ continue;
238
+ output.info(`${info.name}:`);
239
+ if (s.configured) {
240
+ let sourceDesc;
241
+ switch (s.source) {
242
+ case 'keychain':
243
+ sourceDesc = 'System keychain';
244
+ break;
245
+ case 'env':
246
+ sourceDesc = `Environment variable (${s.envVar})`;
247
+ break;
248
+ case 'project-env':
249
+ sourceDesc = `Project .env file (${s.envVar})`;
250
+ break;
251
+ case 'global-env':
252
+ sourceDesc = `Global .env file (~/.bellwether/.env)`;
253
+ break;
254
+ default:
255
+ sourceDesc = s.source;
256
+ }
257
+ output.info(` Status: \u2713 Configured`);
258
+ output.info(` Source: ${sourceDesc}`);
259
+ output.info(` Model: ${DEFAULT_MODELS[s.provider]}`);
260
+ }
261
+ else {
262
+ output.info(` Status: \u2717 Not configured`);
263
+ output.info(` Setup: Run \`bellwether auth\` or set ${info.envVar}`);
264
+ }
265
+ output.newline();
266
+ }
267
+ // Show priority order
268
+ output.info('Credential resolution order:');
269
+ output.info(' 1. Environment variables (highest priority)');
270
+ output.info(' 2. System keychain');
271
+ output.info(' 3. ~/.bellwether/.env file');
272
+ output.info(' 4. Project .env file');
273
+ }
274
+ /**
275
+ * Add a provider.
276
+ */
277
+ async function addProvider(providerArg) {
278
+ const rl = createPrompt();
279
+ let provider;
280
+ if (providerArg && (providerArg === 'openai' || providerArg === 'anthropic')) {
281
+ provider = providerArg;
282
+ }
283
+ else {
284
+ provider = await promptSelect(rl, 'Which provider?', [
285
+ { value: 'anthropic', label: 'Anthropic (recommended)' },
286
+ { value: 'openai', label: 'OpenAI' },
287
+ ]);
288
+ }
289
+ const info = PROVIDER_INFO[provider];
290
+ output.info(`\nGet your API key from: ${info.url}\n`);
291
+ const apiKey = await prompt(rl, `Enter ${info.name} API key: `, true);
292
+ const validation = validateApiKey(provider, apiKey);
293
+ if (!validation.valid) {
294
+ output.error(`\nError: ${validation.error}`);
295
+ rl.close();
296
+ process.exit(EXIT_CODES.ERROR);
297
+ }
298
+ const keychain = getKeychainService();
299
+ await keychain.setApiKey(provider, apiKey);
300
+ output.success(`\n\u2713 ${info.name} API key stored in keychain`);
301
+ rl.close();
302
+ }
303
+ /**
304
+ * Remove a provider.
305
+ */
306
+ async function removeProvider(providerArg) {
307
+ const rl = createPrompt();
308
+ let provider;
309
+ if (providerArg && (providerArg === 'openai' || providerArg === 'anthropic')) {
310
+ provider = providerArg;
311
+ }
312
+ else {
313
+ provider = await promptSelect(rl, 'Which provider to remove?', [
314
+ { value: 'anthropic', label: 'Anthropic' },
315
+ { value: 'openai', label: 'OpenAI' },
316
+ ]);
317
+ }
318
+ const keychain = getKeychainService();
319
+ const deleted = await keychain.deleteApiKey(provider);
320
+ if (deleted) {
321
+ output.success(`\n\u2713 ${PROVIDER_INFO[provider].name} API key removed from keychain`);
322
+ }
323
+ else {
324
+ output.info(`\nNo ${PROVIDER_INFO[provider].name} API key found in keychain`);
325
+ }
326
+ rl.close();
327
+ }
328
+ /**
329
+ * The auth command.
330
+ */
331
+ export const authCommand = new Command('auth')
332
+ .description('Manage LLM provider API keys')
333
+ .addCommand(new Command('status')
334
+ .description('Show authentication status for all providers')
335
+ .action(showStatus))
336
+ .addCommand(new Command('add')
337
+ .description('Add or update an API key')
338
+ .argument('[provider]', 'Provider name (openai, anthropic)')
339
+ .action(addProvider))
340
+ .addCommand(new Command('remove')
341
+ .description('Remove an API key from keychain')
342
+ .argument('[provider]', 'Provider name (openai, anthropic)')
343
+ .action(removeProvider))
344
+ .addCommand(new Command('clear')
345
+ .description('Remove all stored API keys')
346
+ .action(async () => {
347
+ const keychain = getKeychainService();
348
+ await keychain.clearAll();
349
+ output.success('All API keys removed from keychain.');
350
+ }))
351
+ .action(interactiveSetup); // Default action is interactive setup
352
+ //# sourceMappingURL=auth.js.map
@@ -0,0 +1,3 @@
1
+ import { Command } from 'commander';
2
+ export declare const badgeCommand: Command;
3
+ //# sourceMappingURL=badge.d.ts.map
@@ -0,0 +1,74 @@
1
+ import { Command } from 'commander';
2
+ import { createCloudClient } from '../../cloud/client.js';
3
+ import { getLinkedProject } from '../../cloud/auth.js';
4
+ import { EXIT_CODES } from '../../constants.js';
5
+ import * as output from '../output.js';
6
+ export const badgeCommand = new Command('badge')
7
+ .description('Get embeddable badge for your project')
8
+ .option('-p, --project <id>', 'Project ID (uses linked project if not specified)')
9
+ .option('--json', 'Output as JSON')
10
+ .option('--markdown', 'Output markdown only')
11
+ .option('--url', 'Output badge URL only')
12
+ .action(async (options) => {
13
+ // Get project ID
14
+ let projectId = options.project;
15
+ if (!projectId) {
16
+ const link = getLinkedProject();
17
+ if (!link) {
18
+ output.error('No project specified and no linked project found.');
19
+ output.error('Run `bellwether link <project>` first or use --project <id>');
20
+ process.exit(EXIT_CODES.ERROR);
21
+ }
22
+ projectId = link.projectId;
23
+ }
24
+ // Create cloud client
25
+ const client = createCloudClient();
26
+ try {
27
+ const badge = await client.getBadgeInfo(projectId);
28
+ if (!badge) {
29
+ output.error(`Project not found: ${projectId}`);
30
+ process.exit(EXIT_CODES.ERROR);
31
+ }
32
+ if (options.json) {
33
+ output.info(JSON.stringify(badge, null, 2));
34
+ return;
35
+ }
36
+ if (options.markdown) {
37
+ output.info(badge.markdown);
38
+ return;
39
+ }
40
+ if (options.url) {
41
+ output.info(badge.badgeUrl);
42
+ return;
43
+ }
44
+ // Default: formatted output
45
+ output.info('');
46
+ output.info(`Project: ${badge.projectName}`);
47
+ output.info(`Status: ${badge.statusText}`);
48
+ if (badge.lastVerified) {
49
+ output.info(`Verified: ${new Date(badge.lastVerified).toLocaleString()}`);
50
+ }
51
+ if (badge.latestVersion) {
52
+ output.info(`Version: v${badge.latestVersion}`);
53
+ }
54
+ output.info('');
55
+ output.info('Badge URL:');
56
+ output.info(` ${badge.badgeUrl}`);
57
+ output.info('');
58
+ output.info('Add to your README.md:');
59
+ output.info('');
60
+ output.info(` ${badge.markdown}`);
61
+ output.info('');
62
+ output.info('Or with HTML:');
63
+ output.info('');
64
+ // Extract base URL from badge URL for consistency
65
+ const baseUrl = badge.badgeUrl.replace(/\/badge\/.*$/, '');
66
+ output.info(` <a href="${baseUrl}/projects/${projectId}"><img src="${badge.badgeUrl}" alt="Bellwether"></a>`);
67
+ output.info('');
68
+ }
69
+ catch (error) {
70
+ output.error('Failed to get badge info: ' + (error instanceof Error ? error.message : String(error)));
71
+ process.exit(EXIT_CODES.ERROR);
72
+ }
73
+ });
74
+ //# sourceMappingURL=badge.js.map
@@ -0,0 +1,15 @@
1
+ /**
2
+ * baseline accept command - accept detected drift as intentional changes.
3
+ *
4
+ * This command allows users to acknowledge that detected drift was intentional
5
+ * (e.g., when adding new features, updating tool behavior, etc.) and update
6
+ * the baseline to reflect the new expected state.
7
+ *
8
+ * Usage:
9
+ * bellwether baseline accept # Accept drift and update baseline
10
+ * bellwether baseline accept --reason "Added new delete tool"
11
+ * bellwether baseline accept --dry-run # Show what would be accepted
12
+ */
13
+ import { Command } from 'commander';
14
+ export declare const acceptCommand: Command;
15
+ //# sourceMappingURL=baseline-accept.d.ts.map
@@ -0,0 +1,178 @@
1
+ /**
2
+ * baseline accept command - accept detected drift as intentional changes.
3
+ *
4
+ * This command allows users to acknowledge that detected drift was intentional
5
+ * (e.g., when adding new features, updating tool behavior, etc.) and update
6
+ * the baseline to reflect the new expected state.
7
+ *
8
+ * Usage:
9
+ * bellwether baseline accept # Accept drift and update baseline
10
+ * bellwether baseline accept --reason "Added new delete tool"
11
+ * bellwether baseline accept --dry-run # Show what would be accepted
12
+ */
13
+ import { Command } from 'commander';
14
+ import { existsSync, readFileSync } from 'fs';
15
+ import { join } from 'path';
16
+ import { createBaseline, saveBaseline, loadBaseline, compareBaselines, acceptDrift, formatDiffText, } from '../../baseline/index.js';
17
+ import { loadConfig, ConfigNotFoundError } from '../../config/loader.js';
18
+ import { EXIT_CODES } from '../../constants.js';
19
+ import * as output from '../output.js';
20
+ function loadConfigOrExit(configPath) {
21
+ try {
22
+ return loadConfig(configPath);
23
+ }
24
+ catch (error) {
25
+ if (error instanceof ConfigNotFoundError) {
26
+ output.error(error.message);
27
+ process.exit(EXIT_CODES.ERROR);
28
+ }
29
+ throw error;
30
+ }
31
+ }
32
+ /**
33
+ * Load interview result from JSON report.
34
+ */
35
+ function loadInterviewResult(reportPath) {
36
+ if (!existsSync(reportPath)) {
37
+ throw new Error(`Test report not found: ${reportPath}\n\n` +
38
+ 'Run `bellwether check` first to generate a report.\n' +
39
+ 'Configure in bellwether.yaml:\n' +
40
+ ' output:\n' +
41
+ ' format: json # or "both" for JSON + markdown');
42
+ }
43
+ const content = readFileSync(reportPath, 'utf-8');
44
+ let result;
45
+ try {
46
+ result = JSON.parse(content);
47
+ }
48
+ catch (error) {
49
+ throw new Error(`Invalid JSON in report file ${reportPath}: ${error instanceof Error ? error.message : 'Unknown error'}`);
50
+ }
51
+ // Validate that this is a check mode result
52
+ if (result.metadata.model && result.metadata.model !== 'check') {
53
+ throw new Error(`Baseline operations only work with check mode results.\n\n` +
54
+ `The report at ${reportPath} was created with explore mode.\n` +
55
+ 'Run `bellwether check` to generate a check mode report first.');
56
+ }
57
+ return result;
58
+ }
59
+ export const acceptCommand = new Command('accept')
60
+ .description('Accept detected drift as intentional and update the baseline')
61
+ .option('-c, --config <path>', 'Path to config file')
62
+ .option('--report <path>', 'Path to test report JSON file')
63
+ .option('--baseline <path>', 'Path to baseline file')
64
+ .option('--reason <reason>', 'Reason for accepting the drift')
65
+ .option('--accepted-by <name>', 'Who is accepting the drift (for audit trail)')
66
+ .option('--dry-run', 'Show what would be accepted without making changes')
67
+ .option('-f, --force', 'Skip confirmation prompt')
68
+ .action(async (options) => {
69
+ const config = loadConfigOrExit(options.config);
70
+ const outputDir = config.output.dir;
71
+ const resolvedBaselinePath = options.baseline ?? config.baseline.comparePath ?? config.baseline.path;
72
+ if (!resolvedBaselinePath) {
73
+ output.error('No baseline path provided. Set baseline.path or baseline.comparePath in config, or pass --baseline.');
74
+ process.exit(EXIT_CODES.ERROR);
75
+ }
76
+ // Determine paths
77
+ const baselinePath = resolvedBaselinePath.startsWith('/')
78
+ ? resolvedBaselinePath
79
+ : join(outputDir, resolvedBaselinePath);
80
+ const reportPath = options.report || join(outputDir, config.output.files.checkReport);
81
+ // Load the existing baseline
82
+ if (!existsSync(baselinePath)) {
83
+ output.error(`Baseline not found: ${baselinePath}`);
84
+ output.error('\nNo baseline exists to compare against.');
85
+ output.error('Run `bellwether check` followed by `bellwether baseline save` first.');
86
+ process.exit(EXIT_CODES.ERROR);
87
+ }
88
+ let previousBaseline;
89
+ try {
90
+ previousBaseline = loadBaseline(baselinePath);
91
+ }
92
+ catch (error) {
93
+ output.error(`Failed to load baseline: ${error instanceof Error ? error.message : error}`);
94
+ process.exit(EXIT_CODES.ERROR);
95
+ }
96
+ // Load the current test results
97
+ let result;
98
+ try {
99
+ result = loadInterviewResult(reportPath);
100
+ }
101
+ catch (error) {
102
+ output.error(error instanceof Error ? error.message : String(error));
103
+ process.exit(EXIT_CODES.ERROR);
104
+ }
105
+ // Create current baseline from test results
106
+ const serverCommand = result.metadata.serverCommand || 'unknown';
107
+ const currentBaseline = createBaseline(result, serverCommand);
108
+ // Compare baselines
109
+ const diff = compareBaselines(previousBaseline, currentBaseline);
110
+ // Check if there's any drift to accept
111
+ if (diff.severity === 'none') {
112
+ output.success('No drift detected. Baseline is already up to date.');
113
+ return;
114
+ }
115
+ // Show the drift that will be accepted
116
+ output.info('=== Drift to Accept ===');
117
+ output.newline();
118
+ output.info(formatDiffText(diff));
119
+ output.newline();
120
+ // Show summary
121
+ output.info('--- Summary ---');
122
+ output.info(`Severity: ${diff.severity}`);
123
+ if (diff.toolsAdded.length > 0) {
124
+ output.info(`Tools added: ${diff.toolsAdded.join(', ')}`);
125
+ }
126
+ if (diff.toolsRemoved.length > 0) {
127
+ output.warn(`Tools removed: ${diff.toolsRemoved.join(', ')}`);
128
+ }
129
+ if (diff.toolsModified.length > 0) {
130
+ output.info(`Tools modified: ${diff.toolsModified.map((t) => t.tool).join(', ')}`);
131
+ }
132
+ output.info(`Breaking changes: ${diff.breakingCount}`);
133
+ output.info(`Warnings: ${diff.warningCount}`);
134
+ output.info(`Info: ${diff.infoCount}`);
135
+ output.newline();
136
+ // Dry run mode - just show what would happen
137
+ if (options.dryRun) {
138
+ output.info('--- Dry Run Mode ---');
139
+ output.info('Would update baseline with acceptance metadata:');
140
+ output.info(` Accepted by: ${options.acceptedBy || '(not specified)'}`);
141
+ output.info(` Reason: ${options.reason || '(not specified)'}`);
142
+ output.info(` Baseline path: ${baselinePath}`);
143
+ return;
144
+ }
145
+ // For breaking changes without --force, show a warning
146
+ if (diff.severity === 'breaking' && !options.force) {
147
+ output.warn('');
148
+ output.warn('⚠️ This will accept BREAKING changes!');
149
+ output.warn('');
150
+ output.warn('Breaking changes may affect downstream consumers of this MCP server.');
151
+ output.warn('Make sure you have updated any dependent systems accordingly.');
152
+ output.warn('');
153
+ output.warn('To proceed, run again with --force');
154
+ process.exit(EXIT_CODES.ERROR);
155
+ }
156
+ // Accept the drift
157
+ const acceptedBaseline = acceptDrift(currentBaseline, diff, {
158
+ acceptedBy: options.acceptedBy,
159
+ reason: options.reason,
160
+ });
161
+ // Save the updated baseline
162
+ saveBaseline(acceptedBaseline, baselinePath);
163
+ output.success(`Drift accepted and baseline updated: ${baselinePath}`);
164
+ output.newline();
165
+ // Show acceptance details
166
+ output.info('Acceptance recorded:');
167
+ output.info(` Accepted at: ${acceptedBaseline.acceptance?.acceptedAt}`);
168
+ if (options.acceptedBy) {
169
+ output.info(` Accepted by: ${options.acceptedBy}`);
170
+ }
171
+ if (options.reason) {
172
+ output.info(` Reason: ${options.reason}`);
173
+ }
174
+ output.newline();
175
+ output.info('The baseline now reflects the current server state.');
176
+ output.info('Future `bellwether check` runs will compare against this new baseline.');
177
+ });
178
+ //# sourceMappingURL=baseline-accept.js.map
@@ -0,0 +1,12 @@
1
+ /**
2
+ * Baseline migrate command - upgrade baselines to current format version.
3
+ *
4
+ * This command migrates baseline files from older format versions to the
5
+ * current format version, ensuring compatibility with the latest CLI features.
6
+ */
7
+ import { Command } from 'commander';
8
+ /**
9
+ * Create the migrate command.
10
+ */
11
+ export declare const migrateCommand: Command;
12
+ //# sourceMappingURL=baseline-migrate.d.ts.map