Skip to content

CLI reference ​

axiom is the agent CLI from packages/sdk (src/cli.ts). It submits, tracks and resumes actions as an agent, downloads and verifies receipts, and runs the policy simulator.

It never runs in the background and makes no promise that a webhook can restart it. When an action waits on a person, submit returns the pending ID, saves the record and prints how to check it; the next invocation re-authenticates as the same agent (including after key rotation) and carries on.

Developer preview

Not yet published to a registry. From the repository root run it as node packages/sdk/bin/axiom.mjs … (the launcher runs the TypeScript sources through tsx), or alias it: alias axiom="node $PWD/packages/sdk/bin/axiom.mjs". Requires Node 22+.

Configuration ​

Files live in $AXIOM_CONFIG_DIR, else $XDG_CONFIG_HOME/axiom, else ~/.config/axiom:

FileContentsMode
config.jsonSettings below0600
keys/{kid}.jwkPrivate keys from axiom keygen0600, directory 0700
actions.jsonPending action records0600

Files are written to a temporary name and renamed, so a crash never leaves a half-written file.

KeyUsed byMeaning
api_urlall agent commandsAPI origin. Default https://api.sectigoaxiom.com.
agent_idall agent commandsStable agent ID (agt_…).
key_fileall agent commandsPath to the agent's private JWK.
tenantsubmit, simulateDefault tenant ID.
servicesubmit, simulateDefault protected service ID.
project_idsimulateProject for the simulator.
api_keysimulateProject API key (axk_…); AXIOM_API_KEY also works.

Global option: --api URL overrides api_url for one invocation.

Commands ​

axiom keygen ​

Generate an agent signing key. The private key stays on this machine.

OptionDefaultMeaning
--alg ALGES256ES256 or EdDSA.
--agent IDAlso set agent_id in config.

Saves keys/{kid}.jwk, sets key_file, and prints the public JWK to enroll.

Bind the key to the agent next with axiom agent bind (or with axiom agent sign-challenge and the console).

axiom agent bind AGENT_ID ​

Enroll this CLI's key for an agent with proof of possession: fetch a single-use challenge (POST /v1/agents/{id}/credentials/challenge), sign it with the key, and submit the public key and proof (POST /v1/agents/{id}/credentials, kind: "jwk"). The private key never leaves the machine. Earlier active jwk and x509 credentials of the agent enter the rotation overlap window.

Binding is an administrator action (agent.write on the tenant), so the command uses a signed-in console session: pass the axiom_session cookie value from your browser. Prefer the AXIOM_SESSION_COOKIE environment variable to the flag, which can end up in shell history. This is a developer convenience; production enrollment belongs in the console or an automated registration flow.

OptionMeaning
--key FILEPrivate JWK to enroll. Default: config key_file.
--cookie VALUEaxiom_session cookie (or AXIOM_SESSION_COOKIE).
--issue-certificateAlso issue an X.509 client certificate for the key from the CA.
--validity SECONDSRequested credential lifetime (the server and CA may shorten it).
--jsonPrint the credential as JSON.
sh
export AXIOM_SESSION_COOKIE='…'          # axiom_session cookie of a tenant admin
axiom keygen --agent agt_01kd0m6n3b4v5c6x7z8a9s0d1f
axiom agent bind agt_01kd0m6n3b4v5c6x7z8a9s0d1f
# Bound jwk credential crd_… (thumbprint …) to agt_…, valid until 2027-02-13T…

Binding a key that is already bound returns 409 conflict ("this key is already bound to this agent; generate a new key to rotate", or "…to another agent"). To rotate, generate a new key and bind it.

axiom agent sign-challenge CHALLENGE ​

Sign a challenge copied from the console's "bind a key you hold" form and print the proof (a compact JWS) to paste back. CHALLENGE is the payload shown in the console, or the whole challenge response, as JSON or a file holding it.

OptionDefaultMeaning
--key FILEconfig key_filePrivate JWK whose public key is being enrolled.
--typ TYPaxiom-pop+jwsJWS header typ, if the console asks for another.
--agent IDRefuse a challenge issued for any other agent.
sh
axiom agent sign-challenge '{"agent_id":"agt_…","nonce":"…","aud":"https://api.sectigoaxiom.com"}' --agent agt_…

axiom config show and axiom config set KEY VALUE ​

show prints the configuration (with api_key masked) and the directory. set accepts only the keys in the table above.

axiom token ​

Obtain a DPoP-bound access token (private_key_jwt) and print it with its scope and expiry. The token is bound to your key; every request also needs a DPoP proof, so this is for inspection.

axiom submit ​

Submit an action.

OptionMeaning
--operation NAMERequired. E.g. billing.refund.create.
--resource TYPE:IDRequired. E.g. invoice:417.
--service IDDefault: config service.
--tenant IDDefault: config tenant.
--param KEY=VALUEMaterial parameter, repeatable. Values stay strings, so decimals stay exact.
--params-json JSONParameters as a JSON object; --param values are merged over it.
--key OPERATION_KEYOperation key. Default: a new random key, printed so you can retry with it.
--intent TEXTFree-text intent shown to approvers.
--wait SECONDSBounded warm wait; if approved in time, resume and track. Without it, no wait.
--no-executeRecord only; an approved action stays approved until axiom resume.
--jsonPrint JSON ({ kind, status }).
sh
axiom submit --operation billing.refund.create --resource invoice:417 \
  --param amount=25000 --param currency=USD --param beneficiary=acct_acme_ops \
  --intent "Refund the duplicate charge"

Prints the operation key (unless --key or --json), the status line and a description, then what to do next: for a pending action axiom status ID and, once approved, axiom resume ID; for a dispatched one axiom status ID; for a completed one axiom receipt ID --out receipt-ID.json.

axiom status ACTION_ID ​

Authenticated status read. Prints the state, reason and description; for an approved action, the resume command, and a hint if there is no saved request for the ID. --json prints the status.

axiom wait ACTION_ID ​

Bounded warm wait for a decision, capped by the server's max_warm_wait_seconds (25 s). --budget SECONDS, --json. If still waiting, prints when to check again.

axiom resume ACTION_ID ​

Resume an approved action as the original agent, then track it.

OptionMeaning
--resource TYPE:IDDefault: the saved request.
--key OPERATION_KEYDefault: the saved request.
--param KEY=VALUEApproved parameter, repeatable. Default: the saved request.
--params-json JSONApproved parameters as a JSON object.
--wait SECONDSBounded wait for the outcome.
--jsonPrint JSON.

Without a saved record (for example on another machine), pass --key, --resource and the params. The parameters must be exactly the approved ones; a difference is 409 conflict.

axiom pending ​

List actions saved by earlier invocations: ID, last state, operation, resource and deadline.

axiom receipt ACTION_ID ​

Download the signed receipt bundle. --out FILE writes it to a file (and prints the verify command); --reveal FIELDS takes a comma-separated list for a redacted export (e.g. operation,params.amount).

axiom verify BUNDLE_FILE ​

Verify a receipt bundle, offline by default (using the keys embedded in it).

OptionMeaning
--issuer-jwks URLFetch Axiom's keys instead of trusting the bundle snapshot.
--provider-jwks URLFetch the provider's outcome keys.
--trusted-issuer ISSRequire this issuer; repeatable.
--jsonPrint { valid, key_source, report }.

Exits with status 1 when the receipt is not valid.

text
Receipt rcp_01kd0mf…: VALID
  Action      act_01kd0m7s2v8x9yz3abcdefghjk (billing.refund.create on invoice 417)
  Issuer      https://api.sectigoaxiom.com, issued 2026-11-14T18:20:06.000Z
  Agent       agt_01kd0m6n3b4v5c6x7z8a9s0d1f (credential jwk …)
  Tenant      ten_01kd0m4z9x8c7v6b5n4m3l2k1j
  Outcome     succeeded · re_01kd0mf…
  Phases      authorized yes · approved yes · dispatched yes · destination confirmed yes
  Keys        fetched
  Signer      observation key …: valid, key active
  Signer      provider outcome key …: valid
  Checks
    PASS    Axiom observation signature - 1 signature(s) verified
    PASS    Issuer - https://api.sectigoaxiom.com
    PASS    Disclosed fields match commitments - all fields disclosed
    PASS    Request digest - sha-256:…
    PASS    Approval by Finance manager <finance@acme.example> (axiom) - approved, verified via axiom_session
    PASS    Provider outcome attestation - succeeded · re_01kd0mf…

axiom simulate ​

Preview the policy decision for a hypothetical request with a project API key. Creates nothing.

OptionMeaning
--operation NAMERequired.
--resource TYPE:IDRequired.
--service IDDefault: config service.
--tenant IDDefault: config tenant.
--project IDDefault: config project_id.
--api-key KEYDefault: config api_key, or AXIOM_API_KEY.
--agent IDAgent to simulate as.
--grant IDGrant whose rules to apply.
--param KEY=VALUE, --params-json JSONParameters.

Prints the simulator's JSON, including decision.effect, decision.reason_code and the rule trace. Pass --grant to apply a grant's rules (the sample's USD 500 threshold is a grant rule). Without it, grant-level rules are skipped and the response says so in note.

Exit codes and errors ​

0 on success, 1 on any error. Errors print the code and reason, for example error: idempotency_conflict (material_change): … followed by changed fields: params.amount, or field issues for validation_failed. A transport failure says nothing is known about whether the server acted and suggests re-running with the same --key or checking status.

Developer preview. Contract version 2026-11-14.