# Output formats

> Cards, JSON, markdown, --copy, --compact, --verbose — every way CommitBrief renders review findings.

CommitBrief docs · v1.x · Reviewing

Canonical URL: https://commitbrief.com/docs/1.x/output-formats

---

CommitBrief renders review findings in three primary forms. The
choice is driven by global output flags; if none are set and the
destination is a TTY, the colored cards renderer is the default.

## Cards (default TTY)

Lipgloss-styled header / status / footer with one panel per
finding. Each panel is severity-coded (color of the left border)
and includes the finding's title, location, description,
suggestion, and a code snippet when present.

**Triggered when:** TTY stdout AND no `--json` / `--markdown` flag
AND `--color` resolves to ON.

This is the format you see in your terminal during a normal
`commitbrief --staged` session. The output is not designed to be
parsed; it is designed to be read.

## Markdown

Plain markdown — no ANSI escapes, no lipgloss boxes. The same
finding content rendered through the
[OUTPUT.md template](/docs/1.x/review-rules#outputmd--the-markdown-template) (or its
embedded default).

**Triggered by** `--markdown`, by `--color=never`, or by a non-TTY
stdout. The bare `commitbrief --staged > review.md` path also
produces markdown.

The template has access to `.Findings` (typed
`[]Finding{Severity, File, Line, LineEnd, Title, Description,
Suggestion, Language, Snippet}`) plus helpers like
`groupBySeverity`, `upper`, `countFiles`. See
[OUTPUT.md](/docs/1.x/review-rules#outputmd--the-markdown-template) for the template
reference.

## JSON (schema v1)

Strict machine-readable form. Top-level shape:

```json
{
  "schema": "v1",
  "content": "",
  "findings": [
    {
      "severity": "high",
      "file": "internal/handlers/auth.go",
      "line": 42,
      "line_end": 56,
      "title": "Missing authorization check on admin route",
      "description": "...",
      "suggestion": "...",
      "language": "go",
      "snippet": "..."
    }
  ],
  "summary": { "total": 4, "by_severity": { "high": 1, "medium": 3 } },
  "meta": {
    "provider": "anthropic",
    "model": "claude-opus-4-7",
    "lang": "en",
    "tokens": { "input": 2105, "output": 526, "cached": 0 },
    "cost_usd": 0.0731,
    "latency_ms": 4123
  }
}
```

**Triggered by** `--json`. Bypasses cards / markdown renderers
entirely. The schema is **v1**, locked at v1.0.0, and follows
strict semver — additive changes (new optional fields) are allowed
in v1.x; renames, removals, or type changes require a v2 bump.

### Optional `meta` fields

Every field below is `omitempty`: it is absent unless it has
something to report, so a clean review's JSON is byte-for-byte
what it was before these shipped, and the schema stays `1`.

| Field | Since | Meaning |
|-------|-------|---------|
| `meta.baselined` | v1.8.0 | Findings removed by the [baseline](/docs/1.x/signal-control#baseline). |
| `meta.suppressed` | v1.8.0 | Findings removed by an [inline `commitbrief-ignore`](/docs/1.x/signal-control#inline-suppression). |
| `meta.retry_count` | v1.13.0 | How many structured-output repair retries the call needed. Live calls only — a cache replay reports neither this nor `degrade_reason`. |
| `meta.degrade_reason` | v1.13.0 | Why the pipeline fell back to plain markdown, when it did (e.g. `malformed-json`). |
| `meta.filtered_commits` | v1.15.0 | How many commits' patches make up the reviewed diff, when a [commit filter](/docs/1.x/review-scopes#commit-filters-v1150) walked history. |

`--verbose` surfaces `retry_count` and `degrade_reason` as two
footer lines as well, which is what makes retries and degrades
comparable across models.

A [`leaks --json`](/docs/1.x/leaks) report uses this same document
with `meta.provider: "builtin"` and `cost_usd: 0` — there was no
model call — which is why `guard --from-json` consumes it without
any new plumbing.

## CLI-tool-backed providers — plain text passthrough

`claude-cli`, `gemini-cli`, and `codex-cli` emit pre-formatted plain
text from the host CLI, not structured findings. The cards renderer is
skipped; the host CLI's output is streamed verbatim to stdout (or
to `--output <file>`). `--json` and `--markdown` are **rejected
upfront** when paired with a CLI provider — cobra error before any
work runs. See [CLI providers](/docs/1.x/providers#claude-cli-gemini-cli-and-codex-cli).

## Output destinations

| Flag | Effect |
|------|--------|
| `--output <path>` (`-o`) | Write the rendered output to a file. Applies to cards, markdown, JSON, AND plain-text emit (CLI providers). |
| `--copy` | Copy a finding summary to the system clipboard via OSC 52 (works over SSH) plus native tools (`pbcopy` / `wl-copy` / `xclip` / `xsel` / `clip.exe`). Payload format: `[<severity>] <path>:<line>\n<title>\n\n<description>` per finding, joined with `\n---\n\n`. |
| `--compact` | Dense one-line-per-finding output: `[icon] SEVERITY • file:line — title`. Works in cards and markdown modes. |
| `--min-severity <level>` | **Display-only** filter: hide findings below `<level>` in the rendered output (cards, markdown, `--copy`). `--json` stays complete and `--fail-on` still evaluates the full set. See [Severity](/docs/1.x/severity#display-filter----min-severity). |
| `--verbose` (`-v`) | Append a footer with provider / model / tokens / cost / latency. |
| `--quiet` (`-q`) | Suppress stderr info messages (progress, rule-source hints). |

`--json` is a **renderer** choice, not a **destination** choice;
the JSON still goes to stdout (or `--output <file>`). Combine
flags freely:

```sh
commitbrief --staged --json --output review.json --quiet
```

## Color resolution

Default `--color=auto`:

- TTY stdout + no `NO_COLOR` env + no `COMMITBRIEF_NO_COLOR` env →
  color ON.
- Otherwise → color OFF.

`--color=always` forces ON (still overridden by `NO_COLOR` /
`COMMITBRIEF_NO_COLOR`); `--color=never` forces OFF
unconditionally. Color OFF in cards mode falls back to markdown.

## Suggesting a commit message

`--suggest-commit` adds a second step after the review: a free-form
provider call that prints **one** Conventional Commit message for
the staged diff to stdout.

```sh
commitbrief --staged --suggest-commit
```

- **Read-only.** It suggests; you commit. CommitBrief never writes
  to git or the working tree.
- **Staged scope only.** Works with `--staged` or the default run;
  rejected with `--unstaged`, the `diff` subcommand, and with
  `--json` / `--markdown` / `--output` (the suggestion is plain
  stdout, not part of the structured or file output).
- **Any provider.** API providers return the message via a
  free-form path (no JSON contract for this one call); CLI-tool
  providers emit it directly.
- The message follows Conventional Commits (`type(scope): subject`
  plus an optional body). Your `COMMITBRIEF.md` rules govern the
  critique, not the message wording.
- The suggestion is a fresh call each run (not cached); the review
  itself still uses the cache.

## Splash logo

The colored splash logo prints to **stderr** at the start of every
invocation, gated on a TTY-capable stderr. It is NOT part of
stdout — `commitbrief --json | jq` and `commitbrief > out` stay
clean. To suppress it entirely, set `NO_COLOR=1` in the
environment.

## See also

- [Severity and CI gating](/docs/1.x/severity) — what severity
  values can appear and how `--fail-on` maps them to exit codes.
- [Review rules](/docs/1.x/review-rules) — how OUTPUT.md shapes
  the markdown form.
- [Providers](/docs/1.x/providers) — which providers support which
  formats.