The open-source verifier

Every Web Reactions count can be recomputed from public data by a tool you can read and run yourself. The web-reactions-verifier has no privileged access — it sees exactly what you see: the public log, the signed checkpoints, and the public anchors.

What the verifier checks

Point it at the public log and it will, in one run:

What exactly a checkpoint is, and where each piece of data lives, is on the transparency log page.

Verify it yourself

No cloning needed; one command runs the checks above:

npx web-reactions-verify --api https://api.webreactions.app \
  --repo https://raw.githubusercontent.com/khasky/web-reactions-log/main \
  --target github/1

--target also compares one live count against the replayed total; add --ots for the Bitcoin deep audit. The same checks run daily against production and feed the public status page.

The raw entries are also mirrored into the public log repository, so the whole audit can run without contacting our API at all — against a clone, a mirror, or the repo itself:

npx web-reactions-verify --entries repo \
  --repo https://raw.githubusercontent.com/khasky/web-reactions-log/main

In this mode the checkpoint under test comes from the repo's own anchor and every entry from its entries/ shards — nothing we serve live is trusted or even consulted.

Add --stats for a per-day activity report (reactions, distinct pseudonymous authors, revocations) derived from the entries alone — the same series our status page charts, recomputed without us. The verifier also cross-checks the signed daily statistics files we publish to the log repository against what the log itself contains.

Run your own scheduled audit

The verifier repository ships the same GitHub Actions workflow we use: it runs the full verification daily and reports the verdict. Fork web-reactions-verifier, enable Actions on your fork, and set the repository variable LOG_PUBKEY to the key below — from then on your copy audits our production log every day, on infrastructure we don't control. The more independent watchers, the less anyone has to take our word for anything.

The log key

Every checkpoint and daily statistics file is signed with the project's Ed25519 log key. The public half lives in exactly one authoritative place — pinned in the verifier source (and printed in its README) — so the verifier works with no key argument at all. This page deliberately does not restate the value: a copy here could silently drift from the one the tool actually checks against.

Substituting the key would mean tampering with the public verifier repository itself, in the open and under version control, and every historical checkpoint signed with the real key would still expose the swap.

What this proves — and what it doesn't

Strong claims need clear edges. Here is exactly what the cryptography guarantees, and where it stops.

What the math proves

Every count is a replay of public entries — the total is whatever the log adds up to, nothing more. Nothing is removed silently: the only way to change a number is to append a new entry that is signed, anchored, and permanently visible. If the served history ever differs from the anchored one, the verifier fails and tells you where.

What the math can't prove

A revocation carries a public reason_code, but no hash can prove the stated reason is truthful. Cryptography proves what was claimed and when, not that the claim is true. That limit is inherent to any transparency log, and we would rather state it than let you assume otherwise.

Why abuse is still detectable

Like Certificate Transparency, the log is built for detection, not prevention — and detection has teeth here:

Check it yourself

None of the above asks for belief. The log, the checkpoints, and the tooling are public: point the verifier at them and watch it agree.