CLI guide
SpecLogician uses typed "change" commands:
speclogician ch ...applies a change and creates a new state instancespeclogician view ...inspects state componentsspeclogician find ...searches for componentsspeclogician reach ...analyzes scenario reachabilityspeclogician undorolls back changes
All commands accept --json for machine-readable output.
Change commands
Base model
speclogician ch base-edit --src "type state = { x : int; frozen : bool }\ntype action = { amount : int }"
speclogician ch base-edit --file ./base.imlPredicates
speclogician ch pred-add --pred-type state --pred-name balance_ok --pred-src "s.x > 0" \
--description "Account balance is non-negative."
speclogician ch pred-add --pred-type action --pred-name small_order --pred-src "a.amount <= 10000"
# Edit the source, the description, or both. On edit, --pred-src is optional —
# you can update prose without re-supplying the IML body. At least one of
# --pred-src or --description must be provided.
speclogician ch pred-edit --pred-name balance_ok --pred-src "s.x >= 0"
speclogician ch pred-edit --pred-name balance_ok --description "Updated prose only — no body change."
speclogician ch pred-remove --pred-name balance_ok--description is optional, but recommended for predicates whose name and body don't already make the intent obvious (threshold/boundary predicates, anything tied to a magic constant). Skip it when the name is self-evident (is_logged_in).
Transitions
speclogician ch trans-add --trans-name on_order \
--trans-src "{ x = s.x + a.amount; frozen = s.frozen }" \
--description "Apply the order amount to the running position; freeze status unchanged."
# Same as predicates: --trans-src is optional on edit when --description is supplied.
speclogician ch trans-edit --trans-name on_order --trans-src "{ x = s.x + a.amount; frozen = false }"
speclogician ch trans-edit --trans-name on_order --description "Updated prose only."
speclogician ch trans-remove --trans-name on_orderScenarios
speclogician ch scenario-add accept_order --given balance_ok --when small_order --then on_order --goal \
--description "Happy path — a within-limit order is accepted and the position grows."
speclogician ch scenario-add boot --then on_order --initial
speclogician ch scenario-add crash --given invalid_state --then fail --bad \
--description "Safety invariant — the system must never reach this state."
speclogician ch scenario-edit accept_order --given "+new_pred,-balance_ok"
speclogician ch scenario-edit accept_order --description "Updated prose only."
speclogician ch scenario-edit crash --no-bad # remove the bad flag
speclogician ch scenario-remove accept_orderScenario flags: --initial (reachability root), --goal (must be reachable), --bad (must NOT be reachable). Use --no-goal / --no-bad to clear. --description is optional on both add and edit; description-only edits are allowed.
Traces
# Test trace
speclogician ch trace test-add --art-id T1 --name "test positive order" \
--given "{ x = 100; frozen = false }" \
--when "{ amount = 50 }" \
--then "{ x = 150; frozen = false }" \
--filepath "tests/test_orders.py" --language python
# Log trace
speclogician ch trace log-add --art-id L1 --filename "prod.log" \
--given "{ x = 0; frozen = false }" \
--when "{ amount = 100 }" \
--then "{ x = 100; frozen = false }" \
--contents "OrderAccepted qty=100"Data artifacts
# Documentation reference
speclogician ch data doc-add --art-id D1 --text "Orders must be rejected if qty > 10000" --meta "From requirements.md"
# Source code reference
speclogician ch data src-add --art-id S1 --src-code "def check(order): return order.qty <= MAX_QTY" \
--language python --file-path "risk/checks.py"Artifact linking
Link artifacts to the model components they support:
speclogician ch data link --art-id D1 --comp-name small_order
speclogician ch data unlink --art-id D1 --comp-name small_orderBatch operations
Apply multiple changes in one pass. Analysis runs once at the end instead of after each change.
speclogician ch batch --json < changes.json
speclogician ch batch --file changes.json --jsonInput is a JSON array of change objects:
[
{
"kind": "PredicateAdd",
"pred_type": "state",
"pred_name": "x_pos",
"pred_src": "s.x > 0",
"description": "Position is strictly positive."
},
{
"kind": "TransitionAdd",
"trans_name": "step",
"trans_src": "{ x = s.x + a.amount; frozen = s.frozen }",
"description": "Apply the action amount to the position."
},
{
"kind": "ScenarioAdd",
"scenario_name": "sc1",
"description": "Small-order happy path — the position grows by the amount.",
"when": { "add": ["small_order"] },
"then": { "add": ["step"] },
"is_goal": { "set": true }
},
{
"kind": "ScenarioAdd",
"scenario_name": "crash",
"description": "Safety claim — this state must never be reached.",
"given": { "add": ["x_pos"] },
"is_bad": { "set": true }
},
{
"kind": "PredicateEdit",
"pred_name": "x_pos",
"description": "Description-only update — pred_src omitted."
}
]Scenario flags in batch JSON use {"set": true} or {"set": false} for is_initial, is_goal, and is_bad. Omit to leave unchanged.
description is optional on every Add/Edit change. On PredicateEdit and TransitionEdit, both pred_src/trans_src and description are optional — supply at least one. This lets you batch-update prose without touching IML bodies.
Dry run
Validate a batch without applying it:
speclogician ch batch --dry-run --json < changes.jsonReturns { "ok": true, "dry_run": true, "changes_parsed": 3 } on success, or a structured error with change_index on failure.
Undo
Roll back the last change (moves it to an internal stash):
speclogician undo # undo last change
speclogician undo --steps 3 --json # undo 3 changesAgent prompt
Generate the full agent instruction guide:
speclogician prompt # print to stdout
speclogician prompt --out ./prompt.md # write to file