CLI reference
Full command reference for spens
Run a session
spens <environment> <agent> <workspace> [prompt] [options]| Argument or option | Description |
|---|---|
environment | Environment template name (e.g. node-24), or a path to a .json template file |
agent | Agent template name (e.g. pi), or a path to a .json template file |
workspace | Path to the directory to mount as the workspace |
prompt | Optional fourth argument. Runs the agent non-interactively (yolo mode): the agent executes the prompt and exits. The agent template must define a yolo_command |
--rebuild | Rebuild the Docker images from scratch, without cache |
--spens-dir PATH | Directory where session state is stored. Default: <workspace>/.spens |
--config PATH | Use a different spens config file for the session. Default: <workspace>/.spens.config.json. Relative paths resolve against the current directory. The file must exist when given. See The spens config file |
--mcp-config PATH | Inject the MCP servers in a host file (the common mcpServers JSON shape) for this session only. Relative paths resolve against the current directory. Passing it to an agent whose template has no mcp block is a usage error. See Spens with MCP servers |
--mcp-mode MODE | How injected MCP servers combine with the agent's own configuration: merge (default) or replace. The modes an agent supports are declared in its template's mcp block; an unsupported mode is a usage error |
--accept-changes | Auto-accept the agent's workspace changes when the session ends (skips the review prompt) |
--reject-changes | Roll the workspace back to its pre-session state after the agent exits |
--output MODE | Output mode: tty (default, pretty terminal output), jsonl (stream JSON events to stdout), or background (print the session id and exit; the session runs detached) |
--session-id ID | Use a specific session id instead of a random one. Must match ^[a-z0-9][a-z0-9-]{0,31}$; reusing an existing id is an error |
--bypass-config-mounts | Do not mount any of the agent template's configuration files into the agent container. The agent starts with no host configuration/credentials and must log in (or be configured) from inside the session; that state is ephemeral and lost when the container exits |
Notes:
jsonlandbackgroundmodes require a prompt and exactly one of--accept-changes/--reject-changes. Without an explicit decision, the end-of-session change review would block a non-interactive session forever.- Every session writes a machine-readable event stream to
<session_dir>/events.jsonland its current state to<session_dir>/state.json, regardless of output mode.
Session lifecycle commands
spens status <session-id> [--spens-dir PATH] # print session state and exit code
spens cancel <session-id> [--spens-dir PATH] # stop the session and mark it canceled
spens attach <session-id> [--spens-dir PATH] # follow the session event stream until it endsThese work for every spens session, regardless of output mode. Terminal states are finished, canceled, and error.
spens init
spens init [options]| Option | Description |
|---|---|
--yes, -y | Skip all prompts and use defaults for unanswered questions. Requires --stack and --provider |
--stack | Stack used: node, python, dotnet, rust, go, java, manual |
--provider | Model provider(s): fireworks, anthropic, openrouter, openai, google, manual. Comma-separated for multiple (e.g. openai,fireworks) |
--public-get / --no-public-get | Allow or deny public GET access (default: deny) |
--tooling-urls / --no-tooling-urls | Allow or deny the stack's common tooling URLs (default: allow) |
--inject-api-keys / --no-inject-api-keys | Inject the provider's API keys for approved domains (default: allow). Say no when using configurations or subscriptions instead of API keys |
--inject-env / --no-inject-env | Configure the provider's common env vars: forward non-secret vars such as base URLs (default: allow) |
--output PATH | Write the config somewhere other than .spens.config.json |
--force | Overwrite an existing config without asking |
--dry-run | Print the generated config to stdout without writing any file |
The config file that spens init writes — domain rules, secret injection, capture URLs, and the rest — is documented separately in The spens config file.
spens list
spens listPrints all available environments and agents, including local templates found recursively under the workspace templates/ directory. When a local template shadows a built-in one with the same name, the listed entry matches the template that a run would load.
spens log-viewer
spens log-viewer [workspace] [options]| Option | Description |
|---|---|
--port PORT | Port for the web server (default: 7331) |
--host HOST | Host to bind (default: 127.0.0.1) |
--no-browser | Do not open a browser automatically |
--spens-dir PATH | Read sessions from a specific spens directory instead of searching for .spens near the workspace |
spens pricing
spens pricing [options]| Option | Description |
|---|---|
--refresh | Re-fetch every provider's pricing dataset into the local cache |
--vendor | Re-fetch and also update the snapshots shipped in spens/data/pricing (needs a writable checkout) |
--provider NAME | Limit to one provider (repeatable). Providers: anthropic, openai, google, fireworks-ai, openrouter, bedrock |
--model ID | Show the resolved price for one model id |
--tokens N | Context size used to pick a banded model's price with --model |
--offline | Do not fetch; report what cached and vendored data provide |
How costs are computed is described in Pricing.
Spens