Skip to content

JSON report

The versioned machine contract behind --json.

rust-doctor --json .

Paths are workspace-relative. The payload carries no absolute path, no environment variable and no user data, so it is safe to attach to an issue or hand to an agent.

#Top level

{
  "schema_version": 14,
  "audit": { "source_files": 0, "categories": [], "score": {} },
  "status": "complete",
  "complete": true,
  "policy": {},
  "scope": {},
  "project": {},
  "toolchain": {},
  "scan": {},
  "diagnostics": [],
  "delta": null,
  "errors": [],
  "summary": {},
  "gate": {}
}

schema_version is the contract. Branch on it, and accept unknown members: fields are added, never removed or retyped. The frozen archive of an earlier version still projects from the current shape, which is what proves no historical field ever disappeared.

#Reading it correctly

Check complete and errors before trusting audit.score. A pass that fails produces a complete report carrying a ReportError at its stage, with the score's authoritative flag dropped: the number is still there, and it now means less than it appears to.

status distinguishes a scan that finished from one that did not. A status other than complete never means the workspace is clean.

#Counting

summary carries both readings, and they answer different questions:

  • distinct: how many rules fired. This is what the score is computed from.
  • occurrences: how many times they fired. This is the size of the work.

A codebase with one rule violated 218 times has a distinct count of 1. The score moves with the first reading, the effort with the second.

#Diagnostics

Each entry carries id, source, code, base_severity, severity, category, message, help, package, target, path, span, and occurrences.

base_severity is what the catalog ships; severity is what your policy made of it, so the two together show where an override applied. id is the rule identifier and names its producer: clippy::*, rust_doctor::source::*, rust_doctor::cargo::*, rust_doctor::structure::*, rust_doctor::repo::*.

A structural finding reports a family as one diagnostic, with the other members named in its related locations rather than as separate findings.

#Baseline runs

delta is present when the scan ran with --scope baseline or --scope files, and describes what the comparison added. Fingerprints come from normalized content rather than source positions, so inserting lines above an existing finding does not make it look new.