- Get Started

CLI Commands

OpenFlows ships as a single openflows binary. Previous separate binaries such as openflows-setup, openflows-dashboard, and openflows-doctor have been consolidated into subcommands. The binary is the only entry point an operator needs to bootstrap the deployment, manage tenants, and run the autonomous orchestrator.

In development, commands are run through Cargo with cargo run -p openflows --bin openflows -- <command>. In production, the same commands are invoked directly against the compiled binary, typically inside a Docker container or systemd unit. The behavior is identical.

Each worker workspace receives a small openflows-harness binary. It is the only Redis client in the workspace and is never invoked by the operator directly. The openflows binary is the operator-facing CLI; the harness is an implementation detail of the workspace.

Command Overview

CommandPurpose
bootstrapInitialize the deployment, create the admin user, push Coder templates, and verify connectivity.
tenant add <owner/repo>Bind a GitHub repository to a new OpenFlows tenant. Creates the tenant namespace and nexus workspace.
tenant remove <tenant-id>Remove a tenant and stop all of its workers.
tenant listList all configured tenants, repositories, and namespaces.
runStart the autonomous orchestrator in daemon mode. This is the default command.
doctorRun diagnostics on the environment, registry, and Coder/GitHub connectivity.
versionPrint the OpenFlows version and dependency versions.
helpPrint command or subcommand help.

Global Flags

These flags are accepted by most openflows subcommands. They control configuration paths, logging, tenant targeting, and the control-plane API.

FlagPurpose
--config <path>Path to the orchestrator configuration file. Default orchestration/config.yaml.
--registry-path <path>Path to registry.json. Default orchestration/agent/registry.json.
--tenant <tenant-id>Run against a specific tenant. Default is the first configured tenant.
--onceRun a single poll cycle and exit. Useful for cron jobs and testing.
--dry-runDo not create PRs, merge, or destroy workspaces. Plan and log actions only.
--repairRun NEXUS reconcile and repair broken states. Does not pick up new work.
--verbose or -vEnable verbose logging. Equivalent to RUST_LOG=openflows=debug.
--log-level <level>Set the log level (trace, debug, info, warn, error).
--port <port>Port for the OpenFlows control-plane API. Default 8080.
--env-file <path>Load environment variables from an alternate .env file.
--no-apiStart the orchestrator without exposing the control-plane HTTP API.
--helpShow help for a command or subcommand.

bootstrap

openflows bootstrap is the first command you run after starting the infrastructure stack. It creates the OpenFlows admin user in Coder, pushes the openflows-{role} workspace templates, validates the .env configuration, and verifies connectivity to Redis, Coder, and the AI Gateway. It is safe to run multiple times; subsequent runs are idempotent and only update changed templates.

bash
# Development
cargo run -p openflows --bin openflows -- bootstrap

# Production inside the container
openflows bootstrap

Typical output:

text
[INFO] OpenFlows bootstrap v1.2.0
[INFO] Checking Coder connectivity at https://coder.example.com ... OK
[INFO] Checking Redis connectivity at redis://localhost:6379 ... OK
[INFO] Creating admin user openflows-admin ... already exists
[INFO] Pushing template openflows-forge ... updated
[INFO] Pushing template openflows-nexus ... updated
[INFO] Pushing template openflows-sentinel ... updated
[INFO] Pushing template openflows-vessel ... updated
[INFO] Pushing template openflows-lore ... updated
[INFO] AI Gateway reachable ... OK
[INFO] Bootstrap complete. Run: openflows tenant add owner/repo --name my-team

Re-run after template changes

If you modify Coder templates, run openflows bootstrap again to push the updated definitions. Existing running workspaces are not affected; new workspaces will use the updated template.

tenant add

A tenant represents a team working on a specific repository. The tenant add command creates the tenant record, binds it to a GitHub repository, and provisions a dedicated NEXUS workspace. Each tenant is isolated by Coder RBAC and a Redis namespace prefix.

bash
# Add a tenant
openflows tenant add owner/repo --name my-team

# Development
cargo run -p openflows --bin openflows -- tenant add owner/repo --name my-team

Available flags for tenant add:

FlagPurpose
--name <tenant-name>Tenant display name. Used as the Redis namespace and in logs.
--repository <owner/repo>GitHub repository. Can be specified as a positional argument instead.
--coder-user <user>Coder user that owns the tenant. Default is openflows-nexus.
--namespace <namespace>Override the Redis namespace. Default is derived from the tenant name.
--skip-workspaceCreate the tenant record without provisioning the nexus workspace.

Typical output:

text
[INFO] Creating tenant my-team for repository owner/repo
[INFO] Redis namespace: my-team
[INFO] Provisioning nexus workspace for tenant my-team ... workspace-uuid
[INFO] Tenant my-team is active

Repository identity is per tenant

The --repository argument accepts the owner/repo form. The GitHub identity for that repository comes from the Coder external auth provider configured for the tenant's Coder user. OpenFlows does not read or store a GitHub PAT.

tenant remove

tenant remove deletes the tenant record, removes its Redis namespace, and stops any running workers. Workspaces are destroyed. This action is irreversible, but the underlying GitHub repository and issues are not affected.

bash
# Remove a tenant by ID or name
openflows tenant remove my-team

# Development
cargo run -p openflows --bin openflows -- tenant remove my-team

Destructive operation

tenant remove destroys all active workspaces and pending PRs for the tenant. Any in-flight work will be interrupted. Use this command only when you are sure the tenant is no longer needed.

tenant list

tenant list prints all configured tenants, their repositories, namespaces, and the number of active workers. It is a read-only command and can be run safely at any time.

bash
openflows tenant list
text
ID        Repository         Namespace   Active Workers   State
--------  -----------------  ----------  ---------------  -------
my-team   owner/repo         my-team     3                active
team-b    another-org/repo   team-b      0                paused

run

openflows run starts the autonomous orchestrator. In daemon mode, it runs the NEXUS poll loop continuously: discovering issues, assigning workers, provisioning Coder workspaces, running reviews, merging PRs, and tearing down workspaces. It also starts the control-plane HTTP API on the configured port.

bash
# Start in daemon mode
openflows run

# Start with verbose logging and a specific tenant
openflows run --tenant my-team --verbose

# Single-shot mode for cron or GitHub Actions
openflows run --once

# Dry run to test the flow without modifying GitHub
openflows run --dry-run

# Repair mode to reconcile broken state
openflows run --repair

Run Modes

ModeCommandPurpose
Daemonopenflows runContinuously polls for issues, assigns workers, and manages the full lifecycle. Default mode.
Single-shotopenflows run --onceRuns one poll cycle, processes any ready work, and exits. Good for cron or GitHub Actions.
Dry runopenflows run --dry-runPlans actions but does not modify GitHub, merge code, or destroy workspaces.
Repairopenflows run --repairRuns NEXUS reconcile to fix orphaned tickets, stale workers, and unmerged PRs.
No APIopenflows run --no-apiRuns the orchestrator loop without starting the HTTP control-plane server.

--once and --repair are mutually exclusive

--once processes new work for a single cycle. --repair only reconciles existing state. Use them separately; combining them produces an error.

doctor

openflows doctor runs a suite of diagnostics. It checks the .env file, parses the registry, verifies Coder and GitHub connectivity, and reports any misconfigurations. It does not modify state.

bash
# Full diagnostic suite
openflows doctor

# Check only the registry
openflows doctor registry

# Check only Coder connectivity
openflows doctor coder

Doctor is read-only

openflows doctor never provisions workspaces, opens PRs, or deletes data. It is safe to run in production to verify the environment.

version

openflows version prints the binary version, the Coder SDK version, the Rust toolchain version used at build time, and the enabled feature flags. It is useful for debugging compatibility issues.

bash
openflows version
text
OpenFlows v1.2.0
  Coder SDK: v2.x
  Rust toolchain: 1.82
  Features: litellm_fallback, redis_sharedstore, coder_gateway
  Registry schema: v2

update-binaries.sh

./update-binaries.sh is the development helper for keeping the compiled binaries in sync with the Coder templates and workspace images. It builds the openflows and openflows-harness binaries in release mode, then copies them into the template directories so that newly provisioned workspaces receive the latest code.

The script is typically run after pulling new code, after modifying workspace logic, or before testing a change against a real workspace.

bash
# Rebuild and update all binaries and templates
./update-binaries.sh

# The script performs roughly:
# 1. cargo build --release -p openflows -p openflows-harness
# 2. cp target/release/openflows orchestration/templates/bin/
# 3. cp target/release/openflows-harness orchestration/templates/bin/
# 4. docker compose build (if running in Docker)

Restart after updating binaries

After running ./update-binaries.sh, restart the orchestrator container or process so that the new openflows binary is used. Existing running workspaces continue with their old harness binary until they are torn down; new workspaces will pick up the updated one.

Development Commands

Most development workflows use cargo run to invoke the openflows binary directly from the Rust workspace. The following commands are the ones you will use most often.

CommandPurpose
./update-binaries.shRebuild the orchestrator and openflows-harness binaries, then copy them into the Coder templates and workspace images.
cargo run -p openflows --bin openflows -- bootstrapRun the bootstrap command from the workspace in development.
cargo run -p openflows --bin openflows -- tenant add owner/repo --name my-teamAdd a tenant from the development workspace.
cargo run -p openflows --bin openflows -- run --verboseStart the orchestrator in development with verbose logging.
cargo testRun the full Rust test suite.
cargo build --releaseBuild the release binary for production deployment.
cargo clippyRun the Clippy linter.
cargo fmtFormat the Rust codebase.
bash
# Common development workflow
cargo run -p openflows --bin openflows -- bootstrap
cargo run -p openflows --bin openflows -- tenant add my-org/my-repo --name my-team
cargo run -p openflows --bin openflows -- run --verbose

# After making changes to the harness or orchestrator
./update-binaries.sh
cargo run -p openflows --bin openflows -- doctor

Cargo vs. binary

The behavior of cargo run -p openflows --bin openflows -- <command> is identical to openflows <command> after the binary is installed. The only difference is that Cargo rebuilds the binary when source files have changed.

Complete Example

The following command sequence brings up a full OpenFlows deployment from a fresh clone. It assumes Docker Compose is running and the .env file is configured.

bash
# 1. Start the infrastructure stack
-docker compose up -d

# 2. Bootstrap OpenFlows
cargo run -p openflows --bin openflows -- bootstrap

# 3. Add a tenant
cargo run -p openflows --bin openflows -- tenant add owner/repo --name my-team

# 4. Start the orchestrator
cargo run -p openflows --bin openflows -- run --verbose

# 5. After code changes, rebuild and update binaries
./update-binaries.sh

Once the orchestrator is running, create a GitHub issue in the configured repository. NEXUS will detect it on the next poll cycle and the autonomous team will take over.