Keyboard shortcuts

Press ← or → to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

sutra CLI reference

The single sutra binary (crate rust/crates/sutra-cli) carries the whole authoring-to-operations toolchain: scaffolding, validation, packaging, deployment, and analysis. Build it from source:

cd rust && cargo build --release -p sutra-cli    # -> rust/target/release/sutra
cargo run -p sutra-cli -- <args>                  # or run ad hoc

Commands are grouped below by workflow: author → validate → package → deploy → operate → analyze, with the generators last.

Global conventions

ConventionBehavior
--format <FORMAT>text (default) or json for report commands; dot or mermaid for dispatch-graph
-v / -vv / -vvvLog verbosity (info / debug / trace); logs always go to stderr, reports to stdout
Exit 0Clean run, no findings
Exit 1Findings — the input has a diagnosable problem (breaking compat change, routing miss, coverage below threshold)
Exit 2Usage or infrastructure — bad flags, missing files, unparseable input, unreachable database

Database-touching commands (migrate, coverage check/reset, crypto) share one set of connection options, each with an env fallback: --url (SUTRA_DB_URL), --user (SUTRA_DB_USERNAME), --password (SUTRA_DB_PASSWORD), and — for migrate — --schema (SUTRA_DB_SCHEMA). These are the CLI’s own database-connection names, distinct from the engine’s SUTRA_DATASOURCE_* — see Configuration reference.


Author

sutra create app

sutra create app <NAME> [--dir <DIR>]

Scaffolds an application workspace: a sample standalone deployment package under packages/<name>-main/ plus deploy assets (a compose file, a deployments drop-directory, a k8s manifest, a health-gated smoke script). Idempotent-safe — existing files are never overwritten. See Quickstart and Anatomy of an app.

sutra create deployment

sutra create deployment <NAME> [--dir <DIR>] [--from <PACKAGE_DIR>]

Scaffolds a fresh standalone deployment-package skeleton, or copies an existing package with --from — the explicit variant model: packages never inherit, a variant is a copy. See Deployment packages.

sutra create bpmn

sutra create bpmn <PROCESS> [--package <PACKAGE_DIR>] [--validation fatal|soft] [flags]

Generates a process with the validation-gateway wiring (plus accepted/rejected reply templates) into a package, verified through the engine’s own BPMN loader before being written.

FlagMeaning
--validation <MODE>fatal (default): only FATAL outcomes take the rejected branch; soft: FATAL and SOFT_ERRORS both reject
--channel <NAME>Inbound channel the start event subscribes to (default <process>-in)
--message-type <TYPE>Inbound message type (default <Process>Request)
--forceOverwrite an existing user-edited file (never implicit)

sutra create ci

sutra create ci --provider github|bitbucket [--dir <DIR>]

Writes the pipeline for an existing workspace — .github/workflows/sutra.yml or bitbucket-pipelines.yml — as four steps in the order that fails cheapest first:

  1. sutra package over every directory under packages/ — fail-closed validation, so a package the engine would refuse to load never reaches a deployments directory;
  2. sutra generate docs … --check — the committed catalog still matches what it documents;
  3. deploy/smoke.sh against the real engine and the archive just sealed;
  4. publish — the catalog book to GitHub Pages, or printed to a PDF release artifact on a v* tag under Bitbucket.

The provider is explicit rather than detected: a scaffolded pipeline lands in a repository that usually already has one, with its own runners and conventions, and guessing would be guessing wrong in the file most likely to be deleted on sight.

The pipeline checks documentation and never writes it. Regenerating in CI would author bot commits and race step 2 against its own output. When step 2 fails the fix is local — run sutra generate docs and commit the refreshed pages alongside the change that caused them, which is what keeps the diff reviewable.

The release it installs is read from the same distribution seam self-update uses, pinned to the version of the CLI that wrote the file. A distribution’s CLI, its engine image and its release channel are one matched set: a pipeline that fetched some other distribution’s binary would resolve a different codec registry than the archive it had just sealed.


Validate

sutra lint

sutra lint <PACKAGE_DIR>

Runs the full package-time validation suite (the same fail-closed checks sutra package runs) and emits nothing on success. The fast pre-flight before every package.

sutra describe

sutra describe <BPMN_FILE> [--format json]

Prints a structural summary of a BPMN file: processes, events, tasks, gateways, channels. See Troubleshooting BPMN solutions.

sutra dispatch-graph

sutra dispatch-graph <BPMN_FILE> --format dot|mermaid

Emits a graphviz or mermaid diagram of a BPMN file’s dispatch tree.

sutra simulate

sutra simulate <BPMN_FILE> --channel <CHANNEL> --dry-run

Reports which process an inbound channel message would route to. --dry-run is required — routing report only, no execution.

sutra explain

sutra explain [EXPRESSION] [--context <FILE>]

Evaluates a FEEL expression — one-shot, or a REPL on stdin when the expression is omitted. See Rules: DMN, FEEL, and .srl.

sutra compat-baseline

sutra compat-baseline --baseline <PATH_OR_REF> [--current <PATH>] [flags]

Compares current BPMN signatures against a baseline directory or git ref and reports breaking changes — a CI gate on process-contract compatibility between releases.


Package

sutra package

sutra package <INPUT> [-o|--out <DIR>]

Seals a deployment-package directory into one immutable .sutra archive, running the full validation suite fail-closed first. The archive manifest (per-file digests, the content-addressed deployment id) is derived, never authored. See Deployment packages.

sutra deployments list

sutra deployments list <DIR> [--label KEY=VALUE]...

Inspects a directory of sealed .sutra archives — lists each archive’s deployment id and labels.

sutra openapi

sutra openapi <ARCHIVE>

Emits a sealed archive’s generated OpenAPI 3.1 surface (channels → BPMNs, message types, endpoint nature, data stores) — the same document the engine serves live per deployment id.


Deploy

sutra migrate

sutra migrate [status|verify] [--url <URL>] [--dry-run] [flags]

Applies engine schema migrations to the engine-internal database, or inspects them (status — applied vs. pending; verify — ledger integrity, expected head, checksum drift).

sutra crypto provision-dek

sutra crypto provision-dek --key-id <KEY_ID> --kek <REF> [--url <URL>] [flags]

Provisions a KEK-wrapped per-tenant data-encryption key for envelope encryption of sensitive instance variables at rest.

sutra deploy

sutra deploy [ARCHIVE] [flags]

Hot-deploys a sealed .sutra archive onto a running engine. See Deploy, hot-deploy, and rollback and Deployment model for the full mechanics.

FlagMeaning
--apiDeploy via the engine’s synchronous admin API instead of a ConfigMap patch; requires --engine-url
--asyncWith --api: submit async, then poll until Active
--watch <PKG_DIR>Watch a package source directory and re-deploy on change (validate-then-deploy loop); implies --api
--wait / --wait-timeout <SECS>ConfigMap path: poll until Active
--engine-url <URL>Engine base URL for --wait / --api
--api-key <KEY> / --api-key-header <HEADER>Admin auth for --api (default header X-API-Key)
--secret <KEY=VALUE> / --secret-from <FILE>Estate-secret keys ensured/merged before the ConfigMap patch

sutra undeploy

sutra undeploy <DEPLOYMENT> [flags]

Removes a deployment — the engine drains it (no new intake) and retires it at zero instances and zero pending outbox.


Operate and analyze

sutra coverage

sutra coverage init  <FILE> [PROCESS_ID]... [flags]   # seed declarations / scaffold admin set
sutra coverage check [BPMN_FILE] [flags]              # drift lint, or the store-backed check
sutra coverage reset --archive <FILE> [flags]         # re-seed the store covered=false

Path-coverage tooling for q:coverage route declarations (intra-process) and coverage/*.yaml files (cross-process) — see Coverage: declared routes as the compliance signal for the full walkthrough of both shapes and every flag above, and Troubleshooting BPMN solutions for reading a report that doesn’t match what you expected.

sutra test simulate

sutra test simulate --deployments <DIR> --datasource <URL>
                    (--advance <DURATION> | --until-quiescent) [flags]

Boots a real engine on a dynamic port against a directory of sealed deployment archives with a virtual clock installed, fast-forwards it, reports, and shuts down — so a PT24H timer or an R3/PT12H schedule settles in wall-clock seconds. Unrelated to sutra simulate above, which is a dry-run routing report over one BPMN file and boots nothing.

FlagMeaning
--deployments <DIR>Directory of sealed .sutra archives to serve (required)
--datasource <URL> / --datasource-username / --datasource-passwordEngine datasource — the engine’s own SUTRA_DATASOURCE_* env names, not the CLI’s SUTRA_DB_* set (required)
--advance <DURATION>Fast-forward the virtual clock by this ISO-8601 duration, firing everything due along the way, then stop
--until-quiescentFast-forward until nothing is armed and nothing is live, or --timeout elapses
--timeout <DURATION>Real wall-clock budget for the fast-forward loop, either mode (default PT30S)
--start <RFC3339>Virtual start instant (default: the real current instant)
--allow-existing-dataProceed even though the datasource already holds instances

Exactly one of --advance / --until-quiescent is required. Safety: the target database must hold no instances or the run refuses with exit 2 — pointing this at a database with real in-flight instances would durably fire their real timers early; --allow-existing-data is the explicit acknowledgement.

Progress is text on stderr; the final summary is one JSON object on stdout and nothing else touches stdout, so sutra test simulate … | jq . is always safe. See Testing time for the summary’s fields and the embedded seam behind this command.

sutra audit-replay

sutra audit-replay <INSTANCE_ID> --from-jsonl <PATH> [--tenant <TENANT>] [--until <EVENT_TYPE>]

Walks a process instance’s audit events from a JSONL stream — reconstructing what a specific instance did, offline. See Logging and audit.

sutra version

sutra version            # sutra 0.2.0-rc.1
sutra --version          # identical text
sutra version --format json

Prints the tool version. The program name is derived from the running binary, not hardcoded: a distribution that embeds this CLI as a library (sutra_cli::run) under its own binary name prints that name, and one that versions itself independently of the engine (sutra_cli::run_with_version) prints its own version with the embedded engine’s underneath:

<tool> 2.0.0
sutra  0.2.0-rc.1 (engine)

--format json is the structured form and always separates the two — version is the reporting tool’s own, engine the embedded engine’s (equal for this binary):

{"name":"sutra","version":"0.2.0-rc.1","engine":"0.2.0-rc.1"}

Generate

The generators all recompute output that is derived, not authored, and all share one --check drift gate that regenerates without writing — which is the shape a CI or pre-commit gate wants. That shared contract is why they sit under one verb. It is also what separates them from sutra create, which scaffolds files that become yours: a scaffold is headed “edit freely — this file is yours” and needs --force to overwrite your edits, while a generated page is headed “Do not edit above the MANUAL NOTES sentinel” and --check fails the build if you edited it. Two verbs, opposite guarantees — never one.

sutra generate docs

sutra generate docs --input <FOLDER> [--output <DIR>] [--check]

Recurses a folder of authored deployment artifacts — BPMN processes, DMN/.srl rules, Handlebars/XSLT templates and their manifests, channels.yaml, package.yaml, coverage files — and emits a deterministic markdown catalog, one page per artifact. It parses through the engine’s own loaders, so each page describes exactly what the engine loads rather than a second parser’s opinion of it. --check generates into a temporary directory and reports drift instead of writing anything. sutra generate catalog is its sibling for Rust source — same --output / --check contract, one page per source file, rooted at --repo-root. A deployment package wants docs; catalog documents the engine’s own source tree.

Each BPMN page opens with a diagram in BPMN notation, auto-laid-out from the process graph — authored BPMN carries no <bpmndi:BPMNDiagram>, so no coordinates are needed in the source. The SVG is embedded in the page, scaled to the column, and linked to a full-size copy written beside it (<name>.svg) that opens in a new tab.

sutra generate schema-handler

sutra generate schema-handler <SCHEMAS_DIR> <OUT_DIR> [--full] [--check]

Compiles a directory of XSD schemas into Rust sources: the decode tables, the canonical map projection, and the shape metadata a schema-bound codec is built on. The schema files are the only input, and emission is byte-identical run to run after rustfmt — which is what makes --check (regenerate in memory, diff against the tree at <OUT_DIR>, exit 1 on any difference) a usable drift gate. The default emission is the slim, data-driven form; --full additionally emits the typed model. A write run touches only the files the generator itself produces and never the hand-maintained ones alongside them — support.rs and Cargo.toml are yours.

Both paths are arguments, not conventions: it is a neutral tool over whatever corpus you point it at, and the crate it emits lives wherever the caller wants it — including in a repository that composes this one.