opensip-cli 0.1.13 → 0.1.15

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 (181) hide show
  1. package/dist/bootstrap/artifact-retention.d.ts +62 -0
  2. package/dist/bootstrap/artifact-retention.d.ts.map +1 -0
  3. package/dist/bootstrap/artifact-retention.js +117 -0
  4. package/dist/bootstrap/artifact-retention.js.map +1 -0
  5. package/dist/bootstrap/artifact-seams.d.ts +21 -1
  6. package/dist/bootstrap/artifact-seams.d.ts.map +1 -1
  7. package/dist/bootstrap/artifact-seams.js +76 -4
  8. package/dist/bootstrap/artifact-seams.js.map +1 -1
  9. package/dist/bootstrap/atomic-artifact-write.d.ts.map +1 -1
  10. package/dist/bootstrap/atomic-artifact-write.js +7 -2
  11. package/dist/bootstrap/atomic-artifact-write.js.map +1 -1
  12. package/dist/bootstrap/build-command-registration-input.d.ts.map +1 -1
  13. package/dist/bootstrap/build-command-registration-input.js.map +1 -1
  14. package/dist/bootstrap/build-per-run-scope.d.ts.map +1 -1
  15. package/dist/bootstrap/build-per-run-scope.js +3 -0
  16. package/dist/bootstrap/build-per-run-scope.js.map +1 -1
  17. package/dist/bootstrap/bundled-tools.manifest.json +2 -1
  18. package/dist/bootstrap/decorate-tool-primary.d.ts.map +1 -1
  19. package/dist/bootstrap/decorate-tool-primary.js.map +1 -1
  20. package/dist/bootstrap/deliver-envelope.d.ts.map +1 -1
  21. package/dist/bootstrap/deliver-envelope.js +26 -5
  22. package/dist/bootstrap/deliver-envelope.js.map +1 -1
  23. package/dist/bootstrap/dispatch-fork-core.d.ts +15 -2
  24. package/dist/bootstrap/dispatch-fork-core.d.ts.map +1 -1
  25. package/dist/bootstrap/dispatch-fork-core.js +22 -4
  26. package/dist/bootstrap/dispatch-fork-core.js.map +1 -1
  27. package/dist/bootstrap/dispatch-host-rpc-handler.d.ts.map +1 -1
  28. package/dist/bootstrap/dispatch-host-rpc-handler.js +10 -0
  29. package/dist/bootstrap/dispatch-host-rpc-handler.js.map +1 -1
  30. package/dist/bootstrap/io-plane.d.ts.map +1 -1
  31. package/dist/bootstrap/io-plane.js +4 -1
  32. package/dist/bootstrap/io-plane.js.map +1 -1
  33. package/dist/bootstrap/run-plane.d.ts +10 -0
  34. package/dist/bootstrap/run-plane.d.ts.map +1 -1
  35. package/dist/bootstrap/run-plane.js +20 -0
  36. package/dist/bootstrap/run-plane.js.map +1 -1
  37. package/dist/bootstrap/scope-access.d.ts.map +1 -1
  38. package/dist/bootstrap/scope-access.js +4 -1
  39. package/dist/bootstrap/scope-access.js.map +1 -1
  40. package/dist/bootstrap/tool-command-dispatch-types.d.ts +15 -0
  41. package/dist/bootstrap/tool-command-dispatch-types.d.ts.map +1 -1
  42. package/dist/bootstrap/tool-command-worker-config-pass.d.ts.map +1 -1
  43. package/dist/bootstrap/tool-command-worker-config-pass.js.map +1 -1
  44. package/dist/bootstrap/tool-command-worker-context.d.ts +5 -4
  45. package/dist/bootstrap/tool-command-worker-context.d.ts.map +1 -1
  46. package/dist/bootstrap/tool-command-worker-context.js +6 -4
  47. package/dist/bootstrap/tool-command-worker-context.js.map +1 -1
  48. package/dist/bootstrap/tool-command-worker-entry.d.ts.map +1 -1
  49. package/dist/bootstrap/tool-command-worker-entry.js +30 -5
  50. package/dist/bootstrap/tool-command-worker-entry.js.map +1 -1
  51. package/dist/bootstrap/tool-command-worker-rpc.d.ts.map +1 -1
  52. package/dist/bootstrap/tool-command-worker-rpc.js +23 -1
  53. package/dist/bootstrap/tool-command-worker-rpc.js.map +1 -1
  54. package/dist/bootstrap/validate-tool.d.ts.map +1 -1
  55. package/dist/bootstrap/validate-tool.js +4 -1
  56. package/dist/bootstrap/validate-tool.js.map +1 -1
  57. package/dist/cli-context.d.ts.map +1 -1
  58. package/dist/cli-context.js +46 -8
  59. package/dist/cli-context.js.map +1 -1
  60. package/dist/commands/agent-catalog.d.ts +9 -56
  61. package/dist/commands/agent-catalog.d.ts.map +1 -1
  62. package/dist/commands/agent-catalog.js +8 -178
  63. package/dist/commands/agent-catalog.js.map +1 -1
  64. package/dist/commands/assemble-opts.d.ts +13 -0
  65. package/dist/commands/assemble-opts.d.ts.map +1 -0
  66. package/dist/commands/assemble-opts.js +85 -0
  67. package/dist/commands/assemble-opts.js.map +1 -0
  68. package/dist/commands/clear.d.ts.map +1 -1
  69. package/dist/commands/clear.js +12 -2
  70. package/dist/commands/clear.js.map +1 -1
  71. package/dist/commands/configure.d.ts.map +1 -1
  72. package/dist/commands/configure.js +5 -1
  73. package/dist/commands/configure.js.map +1 -1
  74. package/dist/commands/history.d.ts +7 -11
  75. package/dist/commands/history.d.ts.map +1 -1
  76. package/dist/commands/history.js +7 -39
  77. package/dist/commands/history.js.map +1 -1
  78. package/dist/commands/host-command-specs.d.ts.map +1 -1
  79. package/dist/commands/host-command-specs.js +5 -1
  80. package/dist/commands/host-command-specs.js.map +1 -1
  81. package/dist/commands/host-subcommand-groups.d.ts.map +1 -1
  82. package/dist/commands/host-subcommand-groups.js +12 -1
  83. package/dist/commands/host-subcommand-groups.js.map +1 -1
  84. package/dist/commands/host-subcommand-sessions.d.ts.map +1 -1
  85. package/dist/commands/host-subcommand-sessions.js +5 -1
  86. package/dist/commands/host-subcommand-sessions.js.map +1 -1
  87. package/dist/commands/init/agents-md.d.ts +6 -0
  88. package/dist/commands/init/agents-md.d.ts.map +1 -0
  89. package/dist/commands/init/agents-md.js +52 -0
  90. package/dist/commands/init/agents-md.js.map +1 -0
  91. package/dist/commands/init/language-detection.d.ts.map +1 -1
  92. package/dist/commands/init/language-detection.js +5 -1
  93. package/dist/commands/init/language-detection.js.map +1 -1
  94. package/dist/commands/init/scaffold-writer.d.ts.map +1 -1
  95. package/dist/commands/init/scaffold-writer.js +6 -1
  96. package/dist/commands/init/scaffold-writer.js.map +1 -1
  97. package/dist/commands/init.d.ts.map +1 -1
  98. package/dist/commands/init.js +5 -1
  99. package/dist/commands/init.js.map +1 -1
  100. package/dist/commands/mount-command-spec-wiring.d.ts +1 -0
  101. package/dist/commands/mount-command-spec-wiring.d.ts.map +1 -1
  102. package/dist/commands/mount-command-spec-wiring.js +5 -5
  103. package/dist/commands/mount-command-spec-wiring.js.map +1 -1
  104. package/dist/commands/plugin-host-ops.d.ts.map +1 -1
  105. package/dist/commands/plugin-host-ops.js +11 -2
  106. package/dist/commands/plugin-host-ops.js.map +1 -1
  107. package/dist/commands/plugin.d.ts.map +1 -1
  108. package/dist/commands/plugin.js +11 -2
  109. package/dist/commands/plugin.js.map +1 -1
  110. package/dist/commands/session-show.d.ts.map +1 -1
  111. package/dist/commands/session-show.js +13 -81
  112. package/dist/commands/session-show.js.map +1 -1
  113. package/dist/commands/shared.d.ts +3 -1
  114. package/dist/commands/shared.d.ts.map +1 -1
  115. package/dist/commands/suite/capturing-context.d.ts +19 -0
  116. package/dist/commands/suite/capturing-context.d.ts.map +1 -0
  117. package/dist/commands/suite/capturing-context.js +62 -0
  118. package/dist/commands/suite/capturing-context.js.map +1 -0
  119. package/dist/commands/suite/orchestrator.d.ts +12 -0
  120. package/dist/commands/suite/orchestrator.d.ts.map +1 -0
  121. package/dist/commands/suite/orchestrator.js +216 -0
  122. package/dist/commands/suite/orchestrator.js.map +1 -0
  123. package/dist/commands/suite/suite-add.d.ts +18 -0
  124. package/dist/commands/suite/suite-add.d.ts.map +1 -0
  125. package/dist/commands/suite/suite-add.js +130 -0
  126. package/dist/commands/suite/suite-add.js.map +1 -0
  127. package/dist/commands/suite/suite-command-specs.d.ts +4 -0
  128. package/dist/commands/suite/suite-command-specs.d.ts.map +1 -0
  129. package/dist/commands/suite/suite-command-specs.js +150 -0
  130. package/dist/commands/suite/suite-command-specs.js.map +1 -0
  131. package/dist/commands/suite/validate-suite.d.ts +21 -0
  132. package/dist/commands/suite/validate-suite.d.ts.map +1 -0
  133. package/dist/commands/suite/validate-suite.js +89 -0
  134. package/dist/commands/suite/validate-suite.js.map +1 -0
  135. package/dist/commands/tools/install.d.ts.map +1 -1
  136. package/dist/commands/tools/install.js +7 -1
  137. package/dist/commands/tools/install.js.map +1 -1
  138. package/dist/commands/tools/list.d.ts.map +1 -1
  139. package/dist/commands/tools/list.js +54 -31
  140. package/dist/commands/tools/list.js.map +1 -1
  141. package/dist/commands/tools/storage-contract-checks.d.ts.map +1 -1
  142. package/dist/commands/tools/storage-contract-checks.js.map +1 -1
  143. package/dist/commands/tools/uninstall.d.ts.map +1 -1
  144. package/dist/commands/tools/uninstall.js +14 -3
  145. package/dist/commands/tools/uninstall.js.map +1 -1
  146. package/dist/commands/tools/validate.d.ts.map +1 -1
  147. package/dist/commands/tools/validate.js +5 -1
  148. package/dist/commands/tools/validate.js.map +1 -1
  149. package/dist/commands/uninstall/targets.d.ts.map +1 -1
  150. package/dist/commands/uninstall/targets.js +8 -1
  151. package/dist/commands/uninstall/targets.js.map +1 -1
  152. package/dist/commands/uninstall.d.ts.map +1 -1
  153. package/dist/commands/uninstall.js +12 -2
  154. package/dist/commands/uninstall.js.map +1 -1
  155. package/dist/index.js +1 -0
  156. package/dist/index.js.map +1 -1
  157. package/dist/report-compose.js +2 -2
  158. package/dist/report-compose.js.map +1 -1
  159. package/dist/telemetry/sdk-init.d.ts.map +1 -1
  160. package/dist/telemetry/sdk-init.js +3 -1
  161. package/dist/telemetry/sdk-init.js.map +1 -1
  162. package/dist/ui/result-to-view.d.ts.map +1 -1
  163. package/dist/ui/result-to-view.js +33 -0
  164. package/dist/ui/result-to-view.js.map +1 -1
  165. package/dist/ui/views/init-view.d.ts.map +1 -1
  166. package/dist/ui/views/init-view.js +14 -2
  167. package/dist/ui/views/init-view.js.map +1 -1
  168. package/dist/ui/views/misc-views.d.ts.map +1 -1
  169. package/dist/ui/views/misc-views.js +54 -11
  170. package/dist/ui/views/misc-views.js.map +1 -1
  171. package/dist/ui/views/plugin-view.d.ts.map +1 -1
  172. package/dist/ui/views/plugin-view.js +4 -1
  173. package/dist/ui/views/plugin-view.js.map +1 -1
  174. package/dist/ui/views/suite-views.d.ts +6 -0
  175. package/dist/ui/views/suite-views.d.ts.map +1 -0
  176. package/dist/ui/views/suite-views.js +70 -0
  177. package/dist/ui/views/suite-views.js.map +1 -0
  178. package/dist/ui/views/tools-views.d.ts.map +1 -1
  179. package/dist/ui/views/tools-views.js +2 -0
  180. package/dist/ui/views/tools-views.js.map +1 -1
  181. package/package.json +34 -33
@@ -0,0 +1,216 @@
1
+ import { performance } from 'node:perf_hooks';
2
+ import { EXIT_CODES } from '@opensip-cli/contracts';
3
+ import { currentLogger, currentScope, generatePrefixedId, } from '@opensip-cli/core';
4
+ import { buildMaybeDispatchExternal } from '../../bootstrap/bind-external-dispatch.js';
5
+ import { bindToolCliContext } from '../../bootstrap/bind-tool-context.js';
6
+ import { runWithSuiteRunContext } from '../../bootstrap/run-plane.js';
7
+ import { assembleOptsFromSpec } from '../assemble-opts.js';
8
+ import { dispatchOutput } from '../mount-command-spec.js';
9
+ import { createCapturingContext } from './capturing-context.js';
10
+ import { validateSuite } from './validate-suite.js';
11
+ class DirectProcessExit extends Error {
12
+ code;
13
+ constructor(code) {
14
+ super(`process.exit(${code})`);
15
+ this.code = code;
16
+ }
17
+ }
18
+ export async function runSuite(input) {
19
+ const suite = validateSuite({
20
+ name: input.name,
21
+ suite: input.suite,
22
+ tools: input.tools,
23
+ });
24
+ const suiteRunId = generatePrefixedId('suite');
25
+ const started = performance.now();
26
+ const log = currentLogger();
27
+ log.info?.({
28
+ evt: 'cli.suite.run.start',
29
+ suite: suite.name,
30
+ suiteRunId,
31
+ stepCount: suite.steps.length,
32
+ });
33
+ const steps = await runWithSuiteRunContext({ suiteRunId, suiteName: suite.name }, () => runStepsSerially({
34
+ suite,
35
+ suiteRunId,
36
+ ctx: input.ctx,
37
+ suiteOpts: input.suiteOpts,
38
+ }));
39
+ const exitCode = Math.max(0, ...steps.map((step) => step.exitCode));
40
+ const durationMs = Math.max(0, performance.now() - started);
41
+ log.info?.({
42
+ evt: 'cli.suite.run.complete',
43
+ suite: suite.name,
44
+ suiteRunId,
45
+ exitCode,
46
+ durationMs,
47
+ });
48
+ return {
49
+ type: 'suite-run',
50
+ suite: suite.name,
51
+ suiteRunId,
52
+ exitCode,
53
+ durationMs,
54
+ steps,
55
+ };
56
+ }
57
+ async function runStepsSerially(args) {
58
+ const summaries = [];
59
+ let chain = Promise.resolve();
60
+ for (const step of args.suite.steps) {
61
+ chain = chain.then(async () => {
62
+ summaries.push(await runStep({
63
+ suite: args.suite,
64
+ suiteRunId: args.suiteRunId,
65
+ step,
66
+ ctx: args.ctx,
67
+ suiteOpts: args.suiteOpts,
68
+ }));
69
+ });
70
+ }
71
+ await chain;
72
+ return summaries;
73
+ }
74
+ async function runStep(args) {
75
+ const started = performance.now();
76
+ const bound = bindToolCliContext(args.step.tool, args.ctx);
77
+ const capture = createCapturingContext(bound);
78
+ // ADR-0054 out-of-process dispatch must run through the CAPTURING context, not
79
+ // the raw bound ctx. For an external-provenance step the worker replay
80
+ // (`replayResult`) calls `ctx.setExitCode` with the tool's verdict exit code;
81
+ // binding the hook to `capture.context` routes that into the capture's exit slot
82
+ // (`capture.getExitCode()`) so the external step participates in the suite
83
+ // worst-of aggregation exactly like the in-process handler (which already runs
84
+ // against `capture.context`). Binding to `bound` instead dropped the external
85
+ // step's exit code (it never reached the slot, so a findings/regression verdict
86
+ // silently aggregated to 0) AND leaked the code into the outer host context — the
87
+ // same isolation the bundled path preserves. (04↔05 regression: external adapter
88
+ // as a suite step.)
89
+ Object.assign(capture.context, {
90
+ maybeDispatchExternal: buildMaybeDispatchExternal(args.step.tool, capture.context),
91
+ });
92
+ const opts = stepOpts(args.step, args.suiteOpts);
93
+ const hooks = capture.context;
94
+ const diagnostics = currentScope()?.diagnostics;
95
+ const log = currentLogger();
96
+ let errorMessage;
97
+ let exitCode = EXIT_CODES.SUCCESS;
98
+ try {
99
+ diagnostics?.event('execute', 'debug', `suite step '${args.step.spec.name}' started`, {
100
+ suite: args.suite.name,
101
+ suiteRunId: args.suiteRunId,
102
+ tool: args.step.tool.metadata.id,
103
+ command: args.step.spec.name,
104
+ });
105
+ exitCode = await withProcessExitGuard(async () => {
106
+ hooks.resetRun?.();
107
+ hooks.beginRun?.();
108
+ const dispatched = await hooks.maybeDispatchExternal?.(args.step.spec.name, opts, args.step.positionals);
109
+ if (dispatched === true)
110
+ return capture.getExitCode() ?? EXIT_CODES.SUCCESS;
111
+ const result = await args.step.spec.handler(opts, capture.context);
112
+ hooks.completeRun?.(result);
113
+ await dispatchOutput(result, args.step.spec, opts, args.step.positionals, capture.context);
114
+ return capture.getExitCode() ?? EXIT_CODES.SUCCESS;
115
+ }, (code) => {
116
+ // A bundled step called `process.exit(code)` directly: route the code into
117
+ // the capture's last-write-wins slot (the single per-step exit source of
118
+ // truth) just as `setExitCode` would, then record it.
119
+ capture.context.setExitCode(code);
120
+ log.warn?.({
121
+ evt: 'cli.suite.run.step',
122
+ suite: args.suite.name,
123
+ suiteRunId: args.suiteRunId,
124
+ tool: args.step.tool.metadata.id,
125
+ command: args.step.spec.name,
126
+ exitCode: code,
127
+ msg: 'Bundled step called process.exit directly; captured as step verdict.',
128
+ });
129
+ });
130
+ diagnostics?.event('execute', 'debug', `suite step '${args.step.spec.name}' completed`, {
131
+ suite: args.suite.name,
132
+ suiteRunId: args.suiteRunId,
133
+ tool: args.step.tool.metadata.id,
134
+ command: args.step.spec.name,
135
+ exitCode,
136
+ });
137
+ diagnostics?.counter('suite.steps.completed', 1);
138
+ // @fitness-ignore-next-line exit-code-correctness -- suite steps convert thrown step failures into a non-zero step summary; runSuite later returns the max step exit code.
139
+ }
140
+ catch (error) {
141
+ exitCode = EXIT_CODES.RUNTIME_ERROR;
142
+ errorMessage = error instanceof Error ? error.message : String(error);
143
+ diagnostics?.event('execute', 'error', `suite step '${args.step.spec.name}' failed`, {
144
+ suite: args.suite.name,
145
+ suiteRunId: args.suiteRunId,
146
+ tool: args.step.tool.metadata.id,
147
+ command: args.step.spec.name,
148
+ exitCode,
149
+ error: errorMessage,
150
+ });
151
+ log.error?.({
152
+ evt: 'cli.suite.run.step.error',
153
+ suite: args.suite.name,
154
+ suiteRunId: args.suiteRunId,
155
+ tool: args.step.tool.metadata.id,
156
+ command: args.step.spec.name,
157
+ error: errorMessage,
158
+ });
159
+ }
160
+ const durationMs = Math.max(0, performance.now() - started);
161
+ log.info?.({
162
+ evt: 'cli.suite.run.step',
163
+ suite: args.suite.name,
164
+ suiteRunId: args.suiteRunId,
165
+ tool: args.step.tool.metadata.id,
166
+ command: args.step.spec.name,
167
+ exitCode,
168
+ durationMs,
169
+ });
170
+ return {
171
+ tool: args.step.tool.metadata.name,
172
+ stableId: args.step.tool.metadata.id,
173
+ command: args.step.spec.name,
174
+ exitCode,
175
+ durationMs,
176
+ ...(errorMessage === undefined ? {} : { error: errorMessage }),
177
+ };
178
+ }
179
+ function stepOpts(step, suiteOpts) {
180
+ const assembled = assembleOptsFromSpec({
181
+ options: step.spec.options,
182
+ suppliedValues: step.args,
183
+ }).opts;
184
+ const common = {};
185
+ for (const key of step.spec.commonFlags) {
186
+ const value = suiteOpts[key];
187
+ if (value !== undefined)
188
+ common[key] = value;
189
+ }
190
+ if (step.spec.commonFlags.includes('cwd') && common.cwd === undefined) {
191
+ common.cwd = process.cwd();
192
+ }
193
+ return { ...common, ...assembled, _args: step.positionals };
194
+ }
195
+ async function withProcessExitGuard(fn, onDirectExit) {
196
+ // eslint-disable-next-line @typescript-eslint/unbound-method -- process.exit has no `this` contract; identity must be restored after the guard.
197
+ const original = process.exit;
198
+ // @fitness-ignore-next-line throws-documentation -- this private guard intentionally throws a sentinel so direct process.exit calls become suite step exit codes.
199
+ process.exit = (code) => {
200
+ throw new DirectProcessExit(typeof code === 'number' ? code : 0);
201
+ };
202
+ try {
203
+ return await fn();
204
+ }
205
+ catch (error) {
206
+ if (error instanceof DirectProcessExit) {
207
+ onDirectExit(error.code);
208
+ return error.code;
209
+ }
210
+ throw error;
211
+ }
212
+ finally {
213
+ process.exit = original;
214
+ }
215
+ }
216
+ //# sourceMappingURL=orchestrator.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"orchestrator.js","sourceRoot":"","sources":["../../../src/commands/suite/orchestrator.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,18 @@
1
+ import { type Tool } from '@opensip-cli/core';
2
+ export interface SuiteAddInput {
3
+ readonly suite: string;
4
+ readonly tool: string;
5
+ readonly command: string;
6
+ readonly argPairs: readonly string[];
7
+ readonly tools: readonly Tool[];
8
+ readonly projectRoot: string;
9
+ readonly configPath?: string;
10
+ }
11
+ export interface SuiteAddOutput {
12
+ readonly configPath: string;
13
+ readonly changed: boolean;
14
+ readonly tool: Tool;
15
+ readonly args: Readonly<Record<string, unknown>>;
16
+ }
17
+ export declare function addSuiteStep(input: SuiteAddInput): SuiteAddOutput;
18
+ //# sourceMappingURL=suite-add.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"suite-add.d.ts","sourceRoot":"","sources":["../../../src/commands/suite/suite-add.ts"],"names":[],"mappings":"AAIA,OAAO,EAAqC,KAAK,IAAI,EAAE,MAAM,mBAAmB,CAAC;AAKjF,MAAM,WAAW,aAAa;IAC5B,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,QAAQ,EAAE,SAAS,MAAM,EAAE,CAAC;IACrC,QAAQ,CAAC,KAAK,EAAE,SAAS,IAAI,EAAE,CAAC;IAChC,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAC;IAC7B,QAAQ,CAAC,UAAU,CAAC,EAAE,MAAM,CAAC;CAC9B;AAED,MAAM,WAAW,cAAc;IAC7B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAC;IAC1B,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC;IACpB,QAAQ,CAAC,IAAI,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC;CAClD;AAED,wBAAgB,YAAY,CAAC,KAAK,EAAE,aAAa,GAAG,cAAc,CAkBjE"}
@@ -0,0 +1,130 @@
1
+ // @fitness-ignore-file dogfood-one-config-document-ratchet -- `suite add` is the host-owned config authoring command: it intentionally edits opensip-cli.config.yml and does not participate in runtime config loading.
2
+ import { existsSync, readFileSync, statSync, writeFileSync } from 'node:fs';
3
+ import { join } from 'node:path';
4
+ import { ConfigurationError, currentLogger } from '@opensip-cli/core';
5
+ import { isMap, isSeq, parseDocument } from 'yaml';
6
+ const MAX_EDITABLE_CONFIG_BYTES = 1_000_000;
7
+ export function addSuiteStep(input) {
8
+ const tool = resolveTool(input.tool, input.tools);
9
+ const command = tool.commandSpecs?.find((spec) => spec.name === input.command);
10
+ if (command === undefined) {
11
+ throw new ConfigurationError(`Tool '${tool.metadata.name}' has no command '${input.command}'.`, { code: 'CONFIG.SUITE_ADD.UNKNOWN_COMMAND' });
12
+ }
13
+ const configPath = input.configPath ?? join(input.projectRoot, 'opensip-cli.config.yml');
14
+ const args = parseArgPairs(input.argPairs);
15
+ const changed = appendSuiteStep(configPath, input.suite, {
16
+ tool: tool.metadata.id,
17
+ name: tool.metadata.name,
18
+ command: command.name,
19
+ ...(Object.keys(args).length === 0 ? {} : { args }),
20
+ });
21
+ return { configPath, changed, tool, args };
22
+ }
23
+ function resolveTool(selector, tools) {
24
+ const matches = tools.filter((tool) => tool.metadata.id === selector || tool.metadata.name === selector);
25
+ if (matches.length === 1) {
26
+ const [match] = matches;
27
+ if (match !== undefined)
28
+ return match;
29
+ }
30
+ if (matches.length > 1) {
31
+ throw new ConfigurationError(`Tool selector '${selector}' matched multiple tools. Use a UUID.`, {
32
+ code: 'CONFIG.SUITE_ADD.AMBIGUOUS_TOOL',
33
+ });
34
+ }
35
+ throw new ConfigurationError(`Unknown tool '${selector}'.`, {
36
+ code: 'CONFIG.SUITE_ADD.UNKNOWN_TOOL',
37
+ });
38
+ }
39
+ function parseArgPairs(pairs) {
40
+ const args = {};
41
+ for (const pair of pairs) {
42
+ const eq = pair.indexOf('=');
43
+ if (eq <= 0) {
44
+ throw new ConfigurationError(`Invalid --arg '${pair}'. Expected key=value.`, {
45
+ code: 'CONFIG.SUITE_ADD.INVALID_ARG',
46
+ });
47
+ }
48
+ args[pair.slice(0, eq)] = parseScalar(pair.slice(eq + 1));
49
+ }
50
+ return args;
51
+ }
52
+ function parseScalar(raw) {
53
+ if (raw === 'true')
54
+ return true;
55
+ if (raw === 'false')
56
+ return false;
57
+ if (/^-?\d+(\.\d+)?$/.test(raw))
58
+ return Number(raw);
59
+ return raw;
60
+ }
61
+ function appendSuiteStep(configPath, suiteName, step) {
62
+ const doc = readOrCreateDocument(configPath);
63
+ const root = ensureRootMap(doc, configPath);
64
+ let suites = root.get('suites');
65
+ if (!isMap(suites)) {
66
+ suites = doc.createNode({});
67
+ root.set('suites', suites);
68
+ }
69
+ const suitesMap = suites;
70
+ let suite = suitesMap.get(suiteName);
71
+ if (!isMap(suite)) {
72
+ suite = doc.createNode({ steps: [] });
73
+ suitesMap.set(suiteName, suite);
74
+ }
75
+ const suiteMap = suite;
76
+ let seq = suiteMap.get('steps');
77
+ if (seq === undefined) {
78
+ seq = doc.createNode([]);
79
+ suiteMap.set('steps', seq);
80
+ }
81
+ if (!isSeq(seq)) {
82
+ throw new ConfigurationError(`Cannot edit suites.${suiteName}.steps in ${configPath}.`, {
83
+ code: 'CONFIG.SUITE_ADD.INVALID_STEPS',
84
+ });
85
+ }
86
+ const yamlSeq = seq;
87
+ const stepKey = JSON.stringify(step);
88
+ if (yamlSeq.items.some((item) => JSON.stringify(yamlNodeToJson(item)) === stepKey)) {
89
+ currentLogger().info?.({
90
+ evt: 'cli.suite.add.duplicate_step',
91
+ suite: suiteName,
92
+ configPath,
93
+ msg: 'Suite step already exists; leaving config unchanged.',
94
+ });
95
+ return false;
96
+ }
97
+ yamlSeq.add(step);
98
+ writeFileSync(configPath, doc.toString(), 'utf8');
99
+ return true;
100
+ }
101
+ function yamlNodeToJson(item) {
102
+ if (item && typeof item === 'object' && 'toJSON' in item) {
103
+ return item.toJSON();
104
+ }
105
+ return item;
106
+ }
107
+ function readOrCreateDocument(configPath) {
108
+ if (!existsSync(configPath))
109
+ return parseDocument('');
110
+ const stat = statSync(configPath);
111
+ if (stat.size > MAX_EDITABLE_CONFIG_BYTES) {
112
+ throw new ConfigurationError(`Cannot edit ${configPath}: file is larger than ${MAX_EDITABLE_CONFIG_BYTES} bytes.`, { code: 'CONFIG.SUITE_ADD.CONFIG_TOO_LARGE' });
113
+ }
114
+ const doc = parseDocument(readFileSync(configPath, 'utf8'));
115
+ if (doc.errors.length > 0) {
116
+ const first = doc.errors[0]?.message ?? 'unknown YAML error';
117
+ throw new ConfigurationError(`Cannot edit ${configPath}: ${first}.`, {
118
+ code: 'CONFIG.SUITE_ADD.MALFORMED_YAML',
119
+ });
120
+ }
121
+ return doc;
122
+ }
123
+ function ensureRootMap(doc, configPath) {
124
+ doc.contents ??= doc.createNode({});
125
+ if (!isMap(doc.contents)) {
126
+ throw new ConfigurationError(`Cannot edit ${configPath}: opensip-cli.config.yml must start with a YAML map.`, { code: 'CONFIG.SUITE_ADD.NON_MAP_CONFIG' });
127
+ }
128
+ return doc.contents;
129
+ }
130
+ //# sourceMappingURL=suite-add.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"suite-add.js","sourceRoot":"","sources":["../../../src/commands/suite/suite-add.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ import { type HostSpec } from '../host-subcommand-shared.js';
2
+ import type { CliCommandsContext } from '../shared.js';
3
+ export declare function buildSuiteGroupLeaves(ctx: CliCommandsContext): readonly HostSpec[];
4
+ //# sourceMappingURL=suite-command-specs.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"suite-command-specs.d.ts","sourceRoot":"","sources":["../../../src/commands/suite/suite-command-specs.ts"],"names":[],"mappings":"AAIA,OAAO,EAIL,KAAK,QAAQ,EACd,MAAM,8BAA8B,CAAC;AAMtC,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,cAAc,CAAC;AA0JvD,wBAAgB,qBAAqB,CAAC,GAAG,EAAE,kBAAkB,GAAG,SAAS,QAAQ,EAAE,CAElF"}
@@ -0,0 +1,150 @@
1
+ import { suitesConfigSchema } from '@opensip-cli/config';
2
+ import { EXIT_CODES } from '@opensip-cli/contracts';
3
+ import { currentScope } from '@opensip-cli/core';
4
+ import { COMMAND_RESULT, defineCommand, PROJECT_SCOPE, } from '../host-subcommand-shared.js';
5
+ import { runSuite } from './orchestrator.js';
6
+ import { addSuiteStep } from './suite-add.js';
7
+ import { validateSuite } from './validate-suite.js';
8
+ function configuredSuites() {
9
+ return suitesConfigSchema.parse(currentScope()?.configDocument?.suites ?? {});
10
+ }
11
+ function isStringArray(value) {
12
+ return Array.isArray(value) && value.every((item) => typeof item === 'string');
13
+ }
14
+ function parseArg(raw, previous) {
15
+ return [...(isStringArray(previous) ? previous : []), raw];
16
+ }
17
+ function buildSuiteRunSpec(ctx) {
18
+ return defineCommand({
19
+ name: 'run',
20
+ description: 'Run a configured suite in one shared project scope',
21
+ commonFlags: ['cwd', 'json', 'quiet', 'verbose', 'debug', 'reportTo', 'apiKey', 'open'],
22
+ args: [{ name: 'name', description: 'Configured suite name' }],
23
+ scope: PROJECT_SCOPE,
24
+ output: COMMAND_RESULT,
25
+ handler: async (rawOpts) => {
26
+ if (ctx.toolContext === undefined) {
27
+ ctx.setExitCode(EXIT_CODES.CONFIGURATION_ERROR);
28
+ return {
29
+ type: 'error',
30
+ message: 'suite run requires the full ToolCliContext handle.',
31
+ exitCode: EXIT_CODES.CONFIGURATION_ERROR,
32
+ };
33
+ }
34
+ const opts = rawOpts;
35
+ const name = String(opts._args?.[0] ?? '');
36
+ const suite = configuredSuites()[name];
37
+ if (suite === undefined) {
38
+ ctx.setExitCode(EXIT_CODES.CONFIGURATION_ERROR);
39
+ return {
40
+ type: 'error',
41
+ message: `Unknown suite '${name}'.`,
42
+ exitCode: EXIT_CODES.CONFIGURATION_ERROR,
43
+ };
44
+ }
45
+ const result = await runSuite({
46
+ name,
47
+ suite,
48
+ tools: currentScope()?.tools.list() ?? [],
49
+ ctx: ctx.toolContext,
50
+ suiteOpts: opts,
51
+ });
52
+ ctx.setExitCode(result.exitCode);
53
+ return result;
54
+ },
55
+ });
56
+ }
57
+ function buildSuiteListSpec() {
58
+ return defineCommand({
59
+ name: 'list',
60
+ description: 'List configured suites and their resolved steps',
61
+ commonFlags: ['json'],
62
+ scope: PROJECT_SCOPE,
63
+ output: COMMAND_RESULT,
64
+ handler: () => {
65
+ const tools = currentScope()?.tools.list() ?? [];
66
+ const suites = configuredSuites();
67
+ const result = {
68
+ type: 'suite-list',
69
+ totalCount: Object.keys(suites).length,
70
+ suites: Object.entries(suites).map(([name, suite]) => {
71
+ const validated = validateSuite({ name, suite, tools });
72
+ return {
73
+ name,
74
+ ...(suite.description === undefined ? {} : { description: suite.description }),
75
+ steps: validated.steps.map((step) => ({
76
+ tool: step.tool.metadata.name,
77
+ stableId: step.tool.metadata.id,
78
+ command: step.spec.name,
79
+ args: step.args,
80
+ })),
81
+ };
82
+ }),
83
+ };
84
+ return Promise.resolve(result);
85
+ },
86
+ });
87
+ }
88
+ function buildSuiteAddSpec(ctx) {
89
+ return defineCommand({
90
+ name: 'add',
91
+ description: 'Add a tool command step to a configured suite',
92
+ commonFlags: ['json', 'cwd'],
93
+ args: [{ name: 'name', description: 'Suite name' }],
94
+ options: [
95
+ {
96
+ flag: '--tool',
97
+ value: '<name-or-uuid>',
98
+ description: 'Tool name or stable UUID',
99
+ required: true,
100
+ },
101
+ {
102
+ flag: '--command',
103
+ value: '<name>',
104
+ description: 'Tool command name',
105
+ required: true,
106
+ },
107
+ {
108
+ flag: '--arg',
109
+ value: '<key=value>',
110
+ description: 'Tool option value to write into the suite step',
111
+ variadic: true,
112
+ arrayDefault: [],
113
+ parse: parseArg,
114
+ },
115
+ ],
116
+ scope: PROJECT_SCOPE,
117
+ output: COMMAND_RESULT,
118
+ handler: (rawOpts) => {
119
+ const scope = currentScope();
120
+ const opts = rawOpts;
121
+ const suite = String(opts._args?.[0] ?? '');
122
+ const project = scope?.projectContext;
123
+ const output = addSuiteStep({
124
+ suite,
125
+ tool: opts.tool ?? '',
126
+ command: opts.command ?? '',
127
+ argPairs: opts.arg ?? [],
128
+ tools: scope?.tools.list() ?? [],
129
+ projectRoot: project?.projectRoot ?? process.cwd(),
130
+ configPath: project?.configPath,
131
+ });
132
+ const result = {
133
+ type: 'suite-add',
134
+ suite,
135
+ tool: output.tool.metadata.name,
136
+ stableId: output.tool.metadata.id,
137
+ command: opts.command ?? '',
138
+ configPath: output.configPath,
139
+ changed: output.changed,
140
+ };
141
+ if (!output.changed)
142
+ ctx.setExitCode(EXIT_CODES.SUCCESS);
143
+ return result;
144
+ },
145
+ });
146
+ }
147
+ export function buildSuiteGroupLeaves(ctx) {
148
+ return [buildSuiteRunSpec(ctx), buildSuiteListSpec(), buildSuiteAddSpec(ctx)];
149
+ }
150
+ //# sourceMappingURL=suite-command-specs.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"suite-command-specs.js","sourceRoot":"","sources":["../../../src/commands/suite/suite-command-specs.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,21 @@
1
+ import { type CommandSpec, type Tool, type ToolCliContext } from '@opensip-cli/core';
2
+ import type { SuiteDefinition, SuiteStep } from '@opensip-cli/config';
3
+ export interface ValidatedSuiteStep {
4
+ readonly index: number;
5
+ readonly tool: Tool;
6
+ readonly spec: CommandSpec<unknown, ToolCliContext>;
7
+ readonly config: SuiteStep;
8
+ readonly args: Readonly<Record<string, unknown>>;
9
+ readonly positionals: readonly unknown[];
10
+ }
11
+ export interface ValidatedSuite {
12
+ readonly name: string;
13
+ readonly description?: string;
14
+ readonly steps: readonly ValidatedSuiteStep[];
15
+ }
16
+ export declare function validateSuite(args: {
17
+ readonly name: string;
18
+ readonly suite: SuiteDefinition;
19
+ readonly tools: readonly Tool[];
20
+ }): ValidatedSuite;
21
+ //# sourceMappingURL=validate-suite.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"validate-suite.d.ts","sourceRoot":"","sources":["../../../src/commands/suite/validate-suite.ts"],"names":[],"mappings":"AAAA,OAAO,EAEL,KAAK,WAAW,EAChB,KAAK,IAAI,EACT,KAAK,cAAc,EACpB,MAAM,mBAAmB,CAAC;AAI3B,OAAO,KAAK,EAAE,eAAe,EAAE,SAAS,EAAE,MAAM,qBAAqB,CAAC;AAgBtE,MAAM,WAAW,kBAAkB;IACjC,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC;IACpB,QAAQ,CAAC,IAAI,EAAE,WAAW,CAAC,OAAO,EAAE,cAAc,CAAC,CAAC;IACpD,QAAQ,CAAC,MAAM,EAAE,SAAS,CAAC;IAC3B,QAAQ,CAAC,IAAI,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC;IACjD,QAAQ,CAAC,WAAW,EAAE,SAAS,OAAO,EAAE,CAAC;CAC1C;AAED,MAAM,WAAW,cAAc;IAC7B,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,WAAW,CAAC,EAAE,MAAM,CAAC;IAC9B,QAAQ,CAAC,KAAK,EAAE,SAAS,kBAAkB,EAAE,CAAC;CAC/C;AAED,wBAAgB,aAAa,CAAC,IAAI,EAAE;IAClC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,KAAK,EAAE,eAAe,CAAC;IAChC,QAAQ,CAAC,KAAK,EAAE,SAAS,IAAI,EAAE,CAAC;CACjC,GAAG,cAAc,CAuBjB"}