Skip to content

RunOrchestrator — Programmatic Workflow Execution

Use RunOrchestrator to run sequant workflows from Node.js code without going through the CLI. This is the foundation for MCP server integration, SDK consumers, CI scripts, and custom tooling.

  1. sequant initializedsequant init completed in the project
  2. GitHub CLIgh auth status shows authenticated (used for issue fetching)
  3. Node.js 20+node --version

Install sequant as a dependency:

Terminal window
npm install sequant

Import the orchestrator:

import { RunOrchestrator } from 'sequant';

No CLI context, Commander.js, or process globals are required.

The simplest way — handles config resolution, services, worktrees, and cleanup:

import { RunOrchestrator } from 'sequant';
import { getSettings } from 'sequant/lib/settings';
import { getManifest } from 'sequant/lib/manifest';
const settings = await getSettings();
const manifest = await getManifest();
const result = await RunOrchestrator.run(
{
options: { phases: 'spec,exec,qa' },
settings,
manifest: { stack: manifest.stack, packageManager: manifest.packageManager ?? 'npm' },
},
['123', '456'], // issue numbers as strings
);
console.log(`Exit code: ${result.exitCode}`);
for (const r of result.results) {
console.log(`#${r.issueNumber}: ${r.success ? 'passed' : 'failed'}`);
}

For callers that manage their own services and worktrees:

import { RunOrchestrator, buildExecutionConfig, resolveRunOptions } from 'sequant';
const config = buildExecutionConfig(mergedOptions, settings, issueCount);
const orchestrator = new RunOrchestrator({
config,
options: mergedOptions,
issueInfoMap: new Map([[123, { title: 'My issue', labels: [] }]]),
worktreeMap: new Map(),
services: { logWriter: null, stateManager: null },
});
const results = await orchestrator.execute([123]);

Config layers: defaults < settings < env < explicit (CLI flags).

import { resolveRunOptions, ConfigResolver } from 'sequant';
// Quick: merge CLI options with settings
const merged = resolveRunOptions(cliOptions, settings);
// Generic: use ConfigResolver for custom layer merging
const resolver = new ConfigResolver({
defaults: { timeout: 60 },
settings: { timeout: 1800 },
env: { timeout: process.env.SEQUANT_TIMEOUT },
explicit: { timeout: userOverride },
});
const resolved = resolver.resolve();

Pass an onProgress callback to receive per-phase events:

const result = await RunOrchestrator.run(
{
options: {},
settings,
manifest,
onProgress: (issue, phase, event, extra) => {
// event: 'start' | 'complete' | 'failed'
console.log(`#${issue} ${phase}: ${event}`);
},
},
['123'],
);
  • Execution time: 5-20 minutes per issue depending on phases and complexity.
  • Output: RunResult object with per-issue results, log path, exit code, and resolved config. No process.exit is called — the caller decides what to do with failures.
  • Worktrees: Created automatically under ../worktrees/feature/ relative to the project root. Cleaned up on shutdown.
  • Logs: Written to .sequant/logs/ when logJson is enabled in settings.
  • Env vars: SEQUANT_QUALITY_LOOP, SEQUANT_MAX_ITERATIONS, SEQUANT_SMART_TESTS, SEQUANT_TESTGEN are respected as config overrides.

RunOrchestrator.run(init, issueArgs, batches?)

Section titled “RunOrchestrator.run(init, issueArgs, batches?)”

Full lifecycle execution. Handles everything from config resolution to metrics recording.

ParameterTypeRequiredDescription
initRunInitYesSettings, options, manifest, callbacks
issueArgsstring[]YesIssue numbers as strings
batchesnumber[][]NoPre-parsed batch groups (overrides --batch)

Returns Promise<RunResult>.

Low-level dispatch. Caller manages setup and teardown.

ParameterTypeRequiredDescription
issueNumbersnumber[]YesIssues to process

Returns Promise<IssueResult[]>.

Merge CLI options with settings and env. Filters out undefined keys so programmatic callers don’t clobber env/settings values.

ParameterTypeRequiredDescription
cliOptionsRunOptionsYesCaller-provided options (undefined keys are safe)
settingsSequantSettingsYesProject settings

Returns RunOptions.

buildExecutionConfig(mergedOptions, settings, issueCount)

Section titled “buildExecutionConfig(mergedOptions, settings, issueCount)”

Build phase-level execution config from merged options.

ParameterTypeRequiredDescription
mergedOptionsRunOptionsYesOutput of resolveRunOptions
settingsSequantSettingsYesProject settings
issueCountnumberYesNumber of issues (affects parallel mode)

Returns ExecutionConfig.

TypeDescription
RunInitHigh-level init: options, settings, manifest, callbacks
RunResultResults, log path, exit code, worktree/issue maps
IssueResultPer-issue: success, phase results, duration, PR info
OrchestratorConfigLow-level config for new RunOrchestrator()
OrchestratorServicesInjectable services: logWriter, stateManager, shutdownManager
ConfigLayers4-layer config: defaults, settings, env, explicit
ProgressCallback(issue, phase, event, extra?) => void
ModeTriggerBehavior
ParallelMultiple issues, sequential: falseConcurrent execution with p-limit concurrency control
Sequentialsequential: trueOne at a time, stops on first failure
Chainchain: trueSequential with dependency ordering, QA gate support
Batchbatch: ['123,456', '789']Groups executed in order, issues within group run per mode

Import fails with “Cannot find module”

Section titled “Import fails with “Cannot find module””

Symptoms: import { RunOrchestrator } from 'sequant' throws at runtime.

Solution: Ensure sequant is installed and built. Run npm run build in the sequant directory if using a local copy.

Symptoms: Options you set in settings or env vars aren’t taking effect.

Solution: Check config layer priority. Explicit options (passed directly) override env, which overrides settings. If passing options programmatically, omit keys you don’t want to set rather than setting them to undefined.

Symptoms: Error about git worktree conflicts or existing branches.

Solution: Run git worktree list to check for stale worktrees. Clean up with git worktree remove <path> or sequant clean.


Generated for Issue #503 on 2026-04-08