JSON
Every JSON object Tenet prints carries a version. JSON goes to stdout, and with JSON requested, progress and
warnings go to stderr. Each format numbers its versions independently:
| Command | Output | Version |
|---|---|---|
check --json, check --reporter jsonl | One event per line | 4 |
check --dry-run --json | One event per line: selected, combined, then summary | 4 |
status --json | One object | 1 |
show NAME --json, show --pending --json | One object | 2 |
log --json | One review log entry per line | 2 |
export | One evidence packet | 2 |
contracts list --json | One object | 1 |
contracts outdated --json, update --json, diff --json | One object | 1 |
skills outdated --json, update --json, diff --json | One object | 1 |
Compatibility
A format's version changes when a documented field is removed or renamed, when its type changes, or when an existing value starts to mean something else. A release can do the following without a new version:
- Add a field to any object or event. A list that is usually empty, such as a scoped file's
changedorexcerptlines, can be left out when empty; read a missing list as empty. - Add a
checkevent type. - Add a value to a field that names a kind: a conclusion, a review
stateor pendingreason, areason_code, a failurekind, a filestatus, anomittedpart, a log entrytype, or an adoptionstate,change, oroutcome.
Ignore fields and event types you do not know. An unknown kind means the result cannot be interpreted, not that it
passed: treat an unknown conclusion or pending reason as pending, and an unknown file status as needing review. Decide
the outcome from exit_code or the process exit code, which keep the meanings in Output.
Versions are not aligned across formats. Raising every format to one number would change versions that consumers of
check events and status compare against today without changing a field.
Errors
When check, status, show, or log fails with JSON output requested, stdout ends with one check error event,
stderr repeats its message, and the command exits 2. A check that stops partway, such as on rejected credentials,
prints its earlier events first:
{
"version": 4,
"type": "error",
"message": "logging is not part of the current review; see tenet status",
"exit_code": 2
}The event keeps check's version 4 for every command. Look for "type": "error" before reading a status or show
object, which has no type. Other commands report errors on stderr only.
Check
Output describes check events. check --dry-run --json makes no model request and prints:
selectedfor each contract and file:contract,scope,path, a renamed file'sprevious_path,contract_hash,input_bytes,input_limit_bytes,omittedparts, and astatusandreasonfor a file that would be skipped, incomplete, or an error.combinedfor each contract: its repositorycontext, or anerror.summarywithdry_run: true,files,mode,assume_base_valid,deleted,requests, every request the check needs,cached, how many of them earlier answers would answer,max_requests,combined_over_limit,errors, the diff'scoverage, andexit_code. A check sendsrequestsminuscached.
A context lists excerpts when --context supplied only some lines of a file: each
path maps to its supplied inclusive line ranges, as in {"src/storage/query.ts": [[40, 75]]}. A selected file is
listed when its lines took the place of contents left out to fit.
Status
status --json prints the review label, the base commit, the latest revision, unchanged when the working tree
matches the base, contracts, deleted_contracts, and exit_code. Each contract has:
| Field | Meaning |
|---|---|
state | settled, with conclusion and the deciding record (null when the model settled it), or pending, with a reason |
contract, path | The contract's name and document path |
selection | The check whose input this row reports: its revision rev and selected paths |
input | The hash of the contract's current input |
assessed_in | The revision whose model assessment had this input, or null |
model, model_violation, model_answer | That assessment's conclusion, violation probability, and raw answer |
min_confidence | The threshold that check used |
When no check compares the working tree with the base, the object has revision: null, empty contracts,
exit_code: 4, and a message.
Show
show NAME --json prints one contract:
| Field | Meaning |
|---|---|
contract, document | Name, message, path, scope, and hash, and the complete document |
state, selection, mode, scope, input, min_confidence | As in status, plus the check's mode and requested scope |
assessment | The latest model assessment of this input: rev, input, scope, contract_hash, conclusion, carried_from, and file results |
files | Every scoped file: role, path, previous_path, before and after content hashes, error, the changed lines in a diff, the excerpt lines named with --context, and its patch |
records, earlier, older | The latest five records and earlier assessments, and counts of the older ones |
changes_since_earlier | What changed since the latest assessment of a different input |
conclusions | The conclusions record accepts for this mode and scope |
show --pending --json prints contracts, each pending contract in that form without version or file patches,
and changes, the path and patch of each changed file once.
Log
log --json prints each entry of .tenet/events.jsonl, oldest first, with version: 2 and a type of
revision, assessment, or record. A revision's context repeats the --context arguments, including any line
range, as in src/storage/query.ts:40-75.
Contracts
| Command | Fields |
|---|---|
contracts list --json | contracts, each with name, path, scope, and message; contract_changes, the changed contract paths of a diff; and the diff's coverage, null without --base |
contracts outdated --json | contracts, each with path, local name, source, contract, recorded ref, state of its CONTRACT.md (unchanged, adapted, edited, or missing), files, the state of each edited or missing asset, and newest (ref; change of the CONTRACT.md: current, changed, or removed; files, the change of each asset upstream changed, added, or removed; and majors, the highest release of each major crossed, oldest first, where update stops at the first; null offline) |
contracts update --json | contracts, each with path, from, to, the outcome of its CONTRACT.md: unchanged, replaced, merged, conflict with regions, or removed, and files, an object with the outcome of each asset that did not stay unchanged: replaced, added, or removed |
contracts diff PATH --json | contract, with path, the recorded base and the upstream release (each ref, commit, and text; upstream is null when removed), the local text, and files, each asset that differs, with its path and its base, upstream, and local text, each null when that version lacks it |
skills outdated --json and skills update --json print the same objects under skills, and skills diff PATH --json under skill, with skill in place of contract. A skill's path is its installed folder, and its files
cover every file but SKILL.md; an edited Markdown file can also be merged or a conflict. files paths are relative to the copy's
folder, and files is left out when empty. diff reads a file that is not UTF-8 with replacement characters.