Skip to main content
POST
Verifies a proof bundle, derives the claims it backs, and returns the registry calldata for each one. A bundle always backs a KYC claim, whose dataHash is the root itself. It backs one more claim per canonical leaf: RESIDENCY from country, CITIZENSHIP from nationality and ACCREDITATION from investorType. A canonical field proved with the wrong circuit is skipped rather than refused. Add Claim refuses these four slots, so they are filled here or by Attest Proofs.
The registry keeps one claim per slot. Filing a slot replaces the claim already there, whoever wrote it. Use selected to file only the slots you mean to overwrite.
The subject must already be verified on chain, and a wallet whose kycHash on the registry is zero is refused with NOT_VERIFIED. Verify first with Verify Identity. A revoked identity keeps its kycHash and passes this check, but the registry reverts every addClaim for it.
Two root mismatches fail with different codes.ROOT_MISMATCH means the root recomputed from the leaves differs from the root the manifest states, so the bundle is internally inconsistent. HASH_MISMATCH means the manifest’s root differs from the root the registry holds for this wallet, so the bundle belongs to a different batch than the one registered.To file claims from a newer bundle, rotate the registered root with Attest Proofs, which is the endpoint that allows it.
This endpoint, Inspect Manifest and Attest Proofs share one rate limit per instance: 30 requests in a 60-second window, both legs counted. Past it, they answer 429 RATE_LIMITED with a Retry-After header in seconds.

Body Parameters

string
required
The subject. Must already carry a non-zero kycHash on the registry.
object
required
The bundle’s manifest.json, parsed. At most 64 KiB serialized and 32 leaves.
string
The 64 raw bytes of the bundle’s manifest.sig, base64-encoded. Required whenever an operator key is registered. An instance that enforces proofs, which Get Operator Key reports as proofVerificationEnforced, cannot verify a bundle without a registered key. Any other instance without one skips the check.
object
A map of field name to base64 STARK bytes, read from proofs/*.bin. Under enforcement, verification needs one for every leaf you file; the KYC claim needs none, since it is the root itself. Each decoded proof is capped at 256 KiB and all of them together at 4 MiB. Verification also checks a proof sent for a leaf you do not file against that leaf’s proofDigest.
array
Claim type names to file, for example ["KYC", "RESIDENCY"]. Indices are not matched. Omit it, or send an empty array, to file every claim the bundle backs. A selection that matches nothing the bundle proves is refused with NO_SELECTED_CLAIMS.
integer
Days until the claims expire, between 0 and 36500. Omit it, or send 0, and the identity’s own hard expiry is used if it is still in the future. Otherwise the claims do not expire.
array
Send this to confirm. An array of { claimType, txHash }, one per claim you broadcast, with claimType as a name or an index. Omit it to receive the calldata.
array
ERC-3643 register only. One { walletAddress, claimType, signature } per message from a SIGN_MESSAGES answer, with claimType by name. See On an ERC-3643 register.
string
ERC-3643 register only. The instance wallet that signs the claims. It must hold a CLAIM key on the register’s trusted issuer. Omitted, the first instance wallet holding one is used.

The two calls

Without txResults the response is SIGN_TRANSACTIONS with one step per derived claim, KYC first. Each step carries its claimType, dataHash and expiry. Broadcast them from a wallet that holds KYC_PROVIDER_ROLE on the register, then send the same body again with txResults. Before handing out calldata, the API checks that one of your instance’s registered wallets holds that role, and refuses with KYC_PROVIDER_ROLE_MISSING otherwise. It skips the check when the instance has no registered wallet or the role cannot be read. The confirm leg verifies the bundle again, then each receipt independently. A receipt must be a mined, successful addClaim on this instance’s register for this wallet, writing the claim type and data hash derived from the proof. It does not check who signed or which expiry was mined. A step whose hash you omit comes back skipped; one that fails a check comes back failed with a reason; neither stops the others.
success is false when no claim was confirmed, with NO_CLAIMS_ADDED, even though the HTTP status is 200. Read added against total.No ledger row is written here, so List Proofs labels these claims manual. Attest Proofs records which leaf filed each slot.

On an ERC-3643 register

When the instance is bound to an ERC-3643 register, each claim is written to the subject’s ONCHAINID. It must carry a signature from a CLAIM key on the register’s trusted issuer, so the flow gains one round.
  1. The first call answers SIGN_MESSAGES, with one entry in messages per claim. Sign each messageHash as an EIP-191 personal message with a wallet that holds a CLAIM key on claimIssuer.
  2. Call again with claimSignatures. The answer is SIGN_TRANSACTIONS, with one addClaim step per claim addressed to the subject’s ONCHAINID.
  3. Broadcast the steps from the wallet the answer names in signerAddress, then confirm with txResults as above.
An ONCHAINID claim carries no expiry, so expiry is not written on chain. The role check becomes an agent check: one of your instance’s wallets must be an agent of the register. The confirm leg checks that each transaction wrote to this wallet’s ONCHAINID.

Response Fields

object

Verification failures

Every code below means the bundle was rejected and nothing was written on chain. Failures found before the wallet check are never stored: size, shape, version and stub failures, bad proof encoding and an empty selection. VERIFY_BUSY and VERIFY_TIMEOUT are not stored either. Every other verdict, pass or fail, is stored on a verification report. A later request with the same manifest, proof bytes, selection and enforcement setting is answered from that report. That holds until the verifier or the trust anchors change.

Other errors