Inkan Generator & VerifierV1

Generate or verify an Inkan — trust nothing, recompute everything

An Inkan is a permanent fingerprint of a piece of content, together with a picture of that fingerprint. This page is the reference verifier for the standard that defines them, BRC-145, and it is the whole implementation: everything below is computed here, on this device.

Enter a (data, kind) pair and this page renders its canonical seal and its ik1 code — the fingerprint written as text, always ik1 followed by 64 hex characters: that is generation. Add a seal image you were shown and the same render is compared to it pixel-for-pixel: that is verification. A phishing lookalike fails, because it is not the byte-exact render. Both are the same computation, which is why they cannot disagree. No network, no server, no storage: it runs from a local file, a static host, or an on-chain inscription with equal fidelity.

What this page checks: ik1 codes (anchor version 1, SHA-256 over the domain inkan/v1), Seal v3 seals, tamper fingerprints of SPEC §7 (SHA-256; version 1 unless you enter another) and version-1 canary records. Anything newer is refused or reads UNSUPPORTED, never guessed. Text is checked against this browser's Unicode character database.

self-test… recomputed from the standard's pinned vectors on every load

Content anchor — typed commitment & seal

The first layer of the standard. A (data, kind) pair commits to typed content: the kind is folded into the digest, so a seal over an address and a seal over a contract can never collide even when the underlying bytes are identical. Enter a pair to generate its anchor and seal; add the seal image someone showed you to check it pixel-for-pixel.

Peer-to-peer identity checks. Two parties who should be holding the same key, address or handle can each seal it and compare: a mismatch is visible at once. Define your own kind — yourapp:member — and that comparison can never be confused with another application's, because the kind is inside the digest. Per §9 of the standard, treat a visual match as a tamper-notice channel only: it is never sufficient authentication for a value-at-risk decision, and a GENUINE verdict requires the full 32-byte digest — which is what the seal-image comparison below actually does.

Tiers. A kind may carry @t1, @t2 or @t3, choosing how many cells the seal draws: 72, 48 or 24. More cells means more visible entropy and a costlier visual forgery — roughly 279.5 distinct seals at T1, 255.5 at T2 and 231.5 at T3. Reserved kinds have a fixed tier (address is T1, code is T3). Any other string defaults to T2, and so does an unrecognised suffix: @t4 is not a tier, so thing@t4 is simply a kind whose name ends in "@t4", still at T2. Tier changes the picture only. The anchor is the full 32-byte digest at every tier, which is why T3's findable image collisions are a documented design choice rather than a weakness — the digest is what commits, never the picture.

Your Inkan, redrawn as you type. Click it to save the seal.

Download seal PNG Download report

Avalanche — why a lookalike cannot be grown from yours

The seal above is not a picture of your data, it is a picture of its digest, so neighbouring inputs are not neighbouring images. This flips every single bit of whatever is in the sealed-data field, recomputes the cells each time, and reports the fewest that moved — the best an attacker could hope for by nudging the input. The worst case is drawn beside yours, so you can see that even the least dramatic single-bit neighbour is unmistakable.

your data

Code fingerprint — software & build provenance

The second layer of the standard. A release publishes the fingerprint of the exact bytes it shipped; you recompute it here from the file you actually hold. A match proves the code you are running is the code that was released. Different adopters get different digests for identical bytes, because the adopter name is inside the hash.

Warrant canary — is the operator still uncompromised?

The third layer of the standard. A canary is a signed, freshness-proofed statement that the publisher has not been compromised or coerced. Absence, staleness or a bad signature is the warning. The record embeds a recent block height and hash, so it cannot have been signed before that block existed. This page verifies only: it holds no key and can sign nothing.

How to use it. 1. Get the publisher's public key from somewhere you already trust — pinned in an app you installed earlier, a previous release, or handed to you in person. Taking the key from the same page that serves the canary proves nothing, because whoever controls that page controls both. 2. Fetch their latest canary record and signature from wherever they anchor it. On-chain is the point: an inscription or OP_RETURN cannot be quietly withdrawn, so a canary that stops appearing leaves a visible gap instead of vanishing. 3. Paste record, key and signature below and check. 4. Read the verdict, and sanity-check the record yourself: seq should be higher than the last one you saw, and block_height should be recent.

What the verdicts mean. OK — signed by that key and inside the freshness window. STALE — the signature is good but the record is old. The publisher has stopped renewing; that is a warning, not a pass. INVALID — the signature does not verify. Wrong key, altered record, or forgery. UNSUPPORTED — a newer record version than this page implements. Get a newer verifier; it is not a finding against the publisher. MALFORMED — the record, key or signature is not in the form the standard requires, so the signature could not be checked at all. Usually a truncated paste. It is not a pass, and not evidence of forgery. And the one no button can show you: nothing to check at all. If a canary you expect is simply missing, that is the loudest result of all — the design assumes silence is what a coerced publisher is able to produce.

This checks any publisher's canary — paste theirs below. Nothing here is specific to Inkan or to any one project. Load the BRC-145 example if you would rather see it work first; that record is dated 2026-06-30 and will read STALE once it ages past the 35-day window, which is itself worth seeing — it is what a canary nobody renewed looks like.

Paste the record exactly as the publisher published it. The standard fixes its form byte for byte: one line, the seven members in key order, no spaces. A copy that has been re-formatted reads MALFORMED, because a verifier must judge the bytes that were signed. Blank space around the record is ignored.

The record cites a block height and hash, which is what stops it being backdated: it cannot have been signed before that block existed. Checking that needs a fact about the chain, and this page never goes online — so bring one. Enter a height you trust, from your own node or a wallet, and the arithmetic happens here. Leave it blank to skip the check entirely.