Skip to content

refactor: narrow Maestro flow runtime bridge#626

Merged
thymikee merged 4 commits into
mainfrom
refactor/maestro-flow-runtime-boundary
May 30, 2026
Merged

refactor: narrow Maestro flow runtime bridge#626
thymikee merged 4 commits into
mainfrom
refactor/maestro-flow-runtime-boundary

Conversation

@thymikee
Copy link
Copy Markdown
Member

@thymikee thymikee commented May 30, 2026

Summary

  • Replaces the private __maestroRunFlowWhen and __maestroRetry command bridge with replay-owned in-memory control metadata that executes before daemon dispatch.
  • Keeps hooks flattened at parse time and preserves Maestro-specific runtime handling for remaining selector/assertion/gesture/runScript commands.
  • Pins replay-control variable resolution and adds a guard that Maestro compat controls never flow through replay -u serialization.
  • Cleans up leftover flow-control adapter indirection and updates the Maestro compatibility debt map so it no longer documents the deleted batch-step bridge as current architecture.

Touched files: 12.

The remaining Maestro runtime commands still cover behavior that does not map cleanly to native batch/wait/replay semantics yet. I do not see a remaining persistence gap for this PR: Maestro compat flow controls are rejected for replay -u before serialization, and SessionAction.replayControl remains an in-memory execution contract for parsed Maestro YAML.

Validation

  • pnpm exec vitest run --project provider-integration test/integration/provider-scenarios/android-test-suite.test.ts passed.
  • pnpm exec vitest run src/daemon/handlers/__tests__/session-replay-vars.test.ts -t "Maestro compat flow controls|Maestro runFlow.when|Maestro retry|nested Maestro runFlow.when" passed.
  • pnpm exec vitest run src/compat/maestro/__tests__/replay-flow.test.ts src/compat/maestro/__tests__/runtime-flow.test.ts passed.
  • pnpm exec vitest run src/compat/maestro/__tests__/replay-flow.test.ts src/compat/maestro/__tests__/runtime-flow.test.ts src/daemon/handlers/__tests__/session-replay-vars.test.ts -t "Maestro compat flow controls|Maestro runFlow.when|Maestro retry|nested Maestro runFlow.when|visible-gated runFlow|retry commands" passed.
  • pnpm typecheck passed.
  • pnpm exec oxfmt --check src/compat/maestro/flow-control.ts src/compat/maestro/runtime-flow.ts passed.
  • pnpm check:fallow --base origin/main passed.

Note: a broader combined Vitest run that included session-replay-vars.test.ts and Maestro compat tests hit the existing /private/tmp worktree runScript child-process issue: Child process exited before writing stdout.

Copy link
Copy Markdown
Member Author

@thymikee thymikee left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review — narrow Maestro flow runtime bridge

Strong structural improvement. Replacing the stringly-typed __maestroRunFlowWhen / __maestroRetry commands + batchSteps-smuggled-through-flags with a typed SessionAction.replayControl discriminated union is much cleaner, and it lets control-flow-runtime drop its core/dispatch (CommandFlags) dependency entirely. Executing control metadata before daemon dispatch via invokeReplayControl(...) ?? invokeMaestroRuntimeCommand(...) reads well, and retry is now genuinely backend-agnostic rather than Maestro-private — good direction for the broader compat layer.

A few points:

  1. Add an exhaustiveness check to invokeReplayControl. Both switch arms return, so the trailing return undefined is dead code today, but it also means adding a third SessionReplayControl.kind later will silently fall through to undefined (→ dispatched as a literal command) with no compile error. A default: { const _exhaustive: never = control; return undefined; } would turn that into a type error.

  2. Double variable-resolution of nested actions. resolveReplayAction now runs resolveStringProps(action.replayControl, ...), which deep-resolves ${VAR} inside every nested actions[].positionals/flags. Those same nested actions are then resolved again when executed via invokeReplayActionBlockinvokeReplayAction. It's idempotent for normal values, but a resolved value that itself contains ${...} (or any non-idempotent token) would be re-substituted. Probably benign, but a test with a variable used inside a runFlow.when command would pin down the intended single vs. double pass.

  3. Serialization round-trip. SessionAction can now carry a nested SessionAction[] via replayControl. If actions are ever persisted/serialized to artifacts or the session log, confirm the nested structure round-trips (the old batchSteps lived in flags, which presumably already serialized). Just a sanity check, not a known break.

The runFlow.when + retry integration guard is the right thing to add alongside this — though note it duplicates the test added in #620 (see my comment there about picking a single home).

Nice cleanup overall.


Generated by Claude Code

@thymikee thymikee force-pushed the refactor/maestro-flow-runtime-boundary branch from d7dcb1d to 4b472a7 Compare May 30, 2026 13:53
@thymikee
Copy link
Copy Markdown
Member Author

Rebased onto latest main and did another pass on the remaining review points.

  • The exhaustiveness check for invokeReplayControl is in the rebased branch.
  • Nested runFlow.when variable resolution is pinned by the replay-vars tests and still resolves nested actions at execution time.
  • The serialization concern is now guarded explicitly: Maestro compat flow controls are rejected for replay -u before they can cross the replay/session serializer boundary.
  • Removed the duplicate provider-scenario diff that overlapped with test: add Maestro provider integration guards #620 during rebase.

Local validation is reflected in the PR body. CI is running on the rebased head.

@thymikee thymikee merged commit ae73b77 into main May 30, 2026
17 checks passed
@thymikee thymikee deleted the refactor/maestro-flow-runtime-boundary branch May 30, 2026 14:04
@github-actions
Copy link
Copy Markdown

PR Preview Action v1.8.1
Preview removed because the pull request was closed.
2026-05-30 14:04 UTC

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant