@workflow-manager/runner 0.4.0 → 0.4.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/engine.js CHANGED
@@ -6,7 +6,7 @@ import { executeClaudeCodeStep, shouldUseRealClaudeCode } from "./claudeCodeExec
6
6
  import { executeMockStep } from "./mockExecutor.js";
7
7
  import { executeOpencodeStep, shouldUseRealOpencode } from "./opencodeExecutor.js";
8
8
  import { executePiAgentStep } from "./piAgentExecutor.js";
9
- import { validateRuntimeRequirements } from "./runtimePreflight.js";
9
+ import { adapterMockFallbackReason, validateRuntimeRequirements } from "./runtimePreflight.js";
10
10
  function nodeType(step) {
11
11
  if (step.kind === "approval")
12
12
  return "HUMAN";
@@ -302,6 +302,10 @@ async function executeStep(step, input, attempt, workflow, workflowFilePath, hoo
302
302
  if (adapterKey === "claude-code" && shouldUseRealClaudeCode(step)) {
303
303
  return executeClaudeCodeStep(step, input, attempt, workflow, workflowFilePath, hooks);
304
304
  }
305
+ const fallbackReason = adapterMockFallbackReason(step);
306
+ if (fallbackReason) {
307
+ hooks?.onStderr?.(`[wfm] ${step.key}: ${fallbackReason}\n`);
308
+ }
305
309
  return executeMockStep(step, input, attempt, hooks);
306
310
  }
307
311
  export async function runWorkflow(definition, options) {
package/dist/index.js CHANGED
@@ -14,7 +14,7 @@ import { MAN_PAGE_SOURCE } from "./manPage.js";
14
14
  import { promptForApprovalDecision, runWorkflow } from "./engine.js";
15
15
  import { cmdAuth, cmdPublish, cmdPull, cmdRemoteInfo, cmdSearch } from "./remote/commands.js";
16
16
  import { emitRunTelemetryBestEffort } from "./remote/telemetry.js";
17
- import { adapterImplementationStatuses, runtimeDoctorChecks, validateRuntimeRequirements, } from "./runtimePreflight.js";
17
+ import { adapterImplementationStatuses, adapterMockFallbackWarnings, runtimeDoctorChecks, validateRuntimeRequirements, } from "./runtimePreflight.js";
18
18
  function cliDisplayName() {
19
19
  const invokedAs = path.basename(process.argv[1] ?? "");
20
20
  if (invokedAs === "workflow-manager" || invokedAs === "wfm") {
@@ -486,12 +486,14 @@ function cmdDoctor(args) {
486
486
  let workflow = null;
487
487
  let workflowErrors = [];
488
488
  let runtimeErrors = [];
489
+ let adapterWarnings = [];
489
490
  if (workflowPath) {
490
491
  try {
491
492
  workflow = parseWorkflowFile(path.resolve(workflowPath));
492
493
  workflowErrors = validateWorkflow(workflow);
493
494
  if (workflowErrors.length === 0) {
494
495
  runtimeErrors = validateRuntimeRequirements(workflow);
496
+ adapterWarnings = adapterMockFallbackWarnings(workflow);
495
497
  }
496
498
  }
497
499
  catch (err) {
@@ -515,6 +517,7 @@ function cmdDoctor(args) {
515
517
  title: workflow.title,
516
518
  errors: workflowErrors,
517
519
  runtimeErrors,
520
+ adapterWarnings,
518
521
  }
519
522
  : null,
520
523
  baselineErrors,
@@ -548,6 +551,12 @@ function cmdDoctor(args) {
548
551
  else {
549
552
  console.log("- OK workflow schema and runtime requirements");
550
553
  }
554
+ if (adapterWarnings.length > 0) {
555
+ console.log("\nAdapter warnings:");
556
+ for (const warning of adapterWarnings) {
557
+ console.log(`- ${warning.stepKey}: ${warning.message}`);
558
+ }
559
+ }
551
560
  }
552
561
  return exitCode;
553
562
  }
@@ -629,6 +638,9 @@ async function cmdRun(filePath) {
629
638
  });
630
639
  return 1;
631
640
  }
641
+ for (const warning of adapterMockFallbackWarnings(workflow)) {
642
+ process.stderr.write(`⚠ ${warning.stepKey}: ${warning.message}\n`);
643
+ }
632
644
  const objective = getFlag("--objective");
633
645
  const inputRaw = getFlag("--input");
634
646
  let input = {};
@@ -1,4 +1,4 @@
1
- import type { AdapterKey, WorkflowDefinition } from "./types.js";
1
+ import type { AdapterKey, StepDefinition, WorkflowDefinition } from "./types.js";
2
2
  export interface RuntimeDoctorCheck {
3
3
  key: string;
4
4
  label: string;
@@ -13,4 +13,19 @@ export interface AdapterImplementationStatus {
13
13
  }
14
14
  export declare function validateRuntimeRequirements(definition: WorkflowDefinition, env?: NodeJS.ProcessEnv): string[];
15
15
  export declare function runtimeDoctorChecks(env?: NodeJS.ProcessEnv): RuntimeDoctorCheck[];
16
+ export interface AdapterMockFallbackWarning {
17
+ stepKey: string;
18
+ adapter: AdapterKey;
19
+ message: string;
20
+ }
21
+ /**
22
+ * Detects a step that explicitly selects a host-backed adapter whose real
23
+ * execution path is gated behind opt-in payload flags that are not set. Without
24
+ * those flags the engine routes the step to the mock executor; returning a
25
+ * message here lets callers warn instead of silently mocking. Returns null when
26
+ * the step will run as the user expects (default pi-agent, an enabled real
27
+ * adapter, or an intentional mock/codex selection).
28
+ */
29
+ export declare function adapterMockFallbackReason(step: StepDefinition): string | null;
30
+ export declare function adapterMockFallbackWarnings(definition: WorkflowDefinition): AdapterMockFallbackWarning[];
16
31
  export declare function adapterImplementationStatuses(): AdapterImplementationStatus[];
@@ -158,6 +158,37 @@ export function runtimeDoctorChecks(env = process.env) {
158
158
  envCheck("anthropic-key", "Anthropic API key", "ANTHROPIC_API_KEY", env),
159
159
  ];
160
160
  }
161
+ /**
162
+ * Detects a step that explicitly selects a host-backed adapter whose real
163
+ * execution path is gated behind opt-in payload flags that are not set. Without
164
+ * those flags the engine routes the step to the mock executor; returning a
165
+ * message here lets callers warn instead of silently mocking. Returns null when
166
+ * the step will run as the user expects (default pi-agent, an enabled real
167
+ * adapter, or an intentional mock/codex selection).
168
+ */
169
+ export function adapterMockFallbackReason(step) {
170
+ if (step.kind !== "task" || !step.taskSpec?.adapterKey) {
171
+ return null;
172
+ }
173
+ const adapter = resolveTaskAdapter(step.taskSpec.adapterKey);
174
+ if (adapter === "claude-code" && !shouldUseRealClaudeCode(step)) {
175
+ return "adapterKey 'claude-code' is set, but the real Claude Code CLI path is off, so the step runs as a mock. Set taskSpec.payload.useRealAdapter: true to drive the real `claude` CLI.";
176
+ }
177
+ if (adapter === "opencode" && !shouldUseRealOpencode(step)) {
178
+ return "adapterKey 'opencode' is set, but the real OpenCode CLI path is off, so the step runs as a mock. Set taskSpec.payload.useRealAdapter: true and taskSpec.payload.opencodeSmokeTest: true to drive the real `opencode` CLI.";
179
+ }
180
+ return null;
181
+ }
182
+ export function adapterMockFallbackWarnings(definition) {
183
+ const warnings = [];
184
+ for (const step of definition.steps) {
185
+ const message = adapterMockFallbackReason(step);
186
+ if (message) {
187
+ warnings.push({ stepKey: step.key, adapter: resolveTaskAdapter(step.taskSpec?.adapterKey), message });
188
+ }
189
+ }
190
+ return warnings;
191
+ }
161
192
  export function adapterImplementationStatuses() {
162
193
  return [
163
194
  {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@workflow-manager/runner",
3
- "version": "0.4.0",
3
+ "version": "0.4.1",
4
4
  "description": "CLI runner for in-memory and markdown workflow orchestration using ATEP-like envelopes",
5
5
  "repository": {
6
6
  "type": "git",