# Share a TruffleHog Report — Leaked Secrets, Handled Carefully

Canonical: https://commareports.com/share-trufflehog-report
Published: 2026-09-08

> TruffleHog finds verified live credentials. Publishing that list needs more care than any other scan output — here is how to render it, redact it, and share it revocably.

# Share a TruffleHog report

Every other scanner on this site produces a report you should be careful with.
TruffleHog produces one you should be paranoid about.

The difference is verification. TruffleHog does not just pattern-match for
things that look like an AWS key — it calls the provider to check whether the
key still works:

```bash
trufflehog git file://. --only-verified --json > findings.json
trufflehog github --org=acme --only-verified --json > findings.json
trufflehog s3 --bucket=acme-backups --only-verified --json > findings.json
```

A verified finding contains the live credential. That output is not a list of
risks; it is a working set of keys to your infrastructure.

So the first rule of sharing a TruffleHog report is: **do not share the raw
output.**

## Render, redacting as you go

There is no built-in HTML writer, which turns out to be the right shape — the
rendering step is where redaction happens:

```bash
trufflehog git file://. --only-verified --json > findings.json

jq -rs '
  "<h1>Verified secrets</h1><table>
   <tr><th>Detector</th><th>File</th><th>Commit</th><th>Status</th></tr>" +
  (map("<tr><td>\(.DetectorName)</td>
        <td>\(.SourceMetadata.Data.Git.file // "—")</td>
        <td>\(.SourceMetadata.Data.Git.commit[0:12] // "—")</td>
        <td>VERIFIED — rotate</td></tr>") | join("")) +
  "</table>"
' findings.json > report.html
```

Note what is *not* in that template: `.Raw`, `.RawV2`, and `.Redacted`. The
report tells a reader which detector fired, in which file, in which commit —
enough to find and rotate the credential — and does not restate the secret.

Anyone who needs the value itself can get it from the source, under whatever
access controls that source already has.

## Publish it

```bash
curl -fsS -X POST "https://commareports.com/api/v1/reports" \
  -H "Authorization: Bearer $COMMA_API_TOKEN" \
  -H "Content-Type: application/json" \
  -d "$(jq -n --rawfile html report.html \
        --arg t "Verified secrets — acme/api, 2026-09-08" \
        '{title: $t, html: $html}')"
```

Or drag `report.html` into [the app](https://commareports.com/).

**Access: named reviewers.** Not team, not domain-gated, for the initial
report. The set of people who need to see which credentials are live and
unrotated is small and specific. See the [sharing model](/docs/sharing).

## Track rotation, not detection

The finding is the easy part and it is finished the moment the scan completes.
The thing that actually needs a shared artifact is the rotation status, which is
where these incidents usually stall — someone finds nine leaked keys, rotates
six, and nobody can later say which three were left.

A thread per finding turns that into a record:

- "Rotated 2026-09-08 14:20, old key deleted in IAM" — done.
- "This is a test fixture, value is a placeholder from the SDK docs" — false
  positive, argued once, on the record.
- "Cannot rotate until the batch job is redeployed — INF-902" — the one that
  needs following up.

See [commenting on HTML](/comment-on-html). Resolve the thread when the key is
dead, and the unresolved threads are your remaining exposure.

## In CI, gate but still publish

```bash
trufflehog git file://. --since-commit "$BASE_SHA" --only-verified --json > findings.json
# …render report.html, redacting…

curl -fsS -X PATCH "https://commareports.com/api/v1/reports/$REPORT_ID" \
  -H "Authorization: Bearer $COMMA_API_TOKEN" \
  -H "Content-Type: application/json" \
  -d "$(jq -n --rawfile html report.html \
        --arg t "Secret scan — $GITHUB_REF_NAME" '{title: $t, html: $html}')"

[ "$(jq -s length findings.json)" -eq 0 ]   # fail the build after publishing
```

Publish first, then fail. A gate that blocks the build without leaving a
readable report behind is a gate that gets bypassed with `--no-verify`.

## Limits

- **Entry HTML: 5 MB.** A redacted findings table is small; a first scan of a
  long git history with unverified findings included is not — which is another
  reason to publish `--only-verified`.
- **60 requests/minute per token.**

## Try it

Comma is free — unlimited reports, unlimited commenters, unlimited revision
history.

**[Publish a scan privately →](https://commareports.com/)**

### Related

- [Share a Gitleaks report](/share-gitleaks-report) · [Share a security scan report](/share-security-scan-report)
- [Share a SARIF report](/share-sarif-report) · [Share a Semgrep report](/share-semgrep-report)
- [Share a pentest report](/share-pentest-report) · [Scoped tokens for AI agents](/agents/scoped-tokens-for-ai-agents)
