> For the complete documentation index, see [llms.txt](https://docs.t-rex.network/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.t-rex.network/identity-onchainid/claims-issuance-validity-revocation.md).

# Claims: issuance, validity, revocation

Claims are the credentials that make eligibility decidable. A claim is a signed attestation by an issuer about a subject identity: it has passed KYC, its holder is accredited, it resides in a given jurisdiction. The register consults claims to decide whether an identity may hold an asset. This page describes what a claim contains, how it reaches an identity, how its validity is decided, and how it ends.

How the register uses claims is described in [Eligibility and compliance: the two gates](/the-primary-register/eligibility-and-compliance-the-two-gates.md). How an issuer comes to be trusted is described in [Claim issuers, trust and reputation](/identity-onchainid/claim-issuers-trust-and-reputation.md).

## What a claim contains

| Field             | Meaning                                                                                                                                        |
| ----------------- | ---------------------------------------------------------------------------------------------------------------------------------------------- |
| `topic`           | A number that stands for the fact being attested. An asset requires topics, not particular claims.                                             |
| `issuer`          | The address of the issuer: the ONCHAINID of a Claim Issuer, or a contract that implements the claim issuer interface.                          |
| `signature`       | The issuer's signature, carried together with the signer that produced it.                                                                     |
| `data.issuedAt`   | When the claim was signed. The claim is not valid before it.                                                                                   |
| `data.validUntil` | When the claim expires. Zero means no expiry.                                                                                                  |
| `data.payload`    | The content of the claim for its topic.                                                                                                        |
| `scheme`, `uri`   | How the claim is to be interpreted, and where supporting material can be found. Both are covered by the signature through `data.metadataHash`. |

A claim is stored on the identity it is about. It is identified by `keccak256(abi.encode(issuer, topic))`, so an identity holds at most one claim per issuer and topic. Adding a claim from the same issuer for the same topic replaces the previous one.

> **No personal data.** A claim says that an issuer vouches for a fact about an identity. The payload is a hash or an encoded value, not raw personal data. The documents behind the claim stay off-chain with the issuer. The signature, the payload and the URI are each limited to 2,048 bytes.

## What the issuer signs

The issuer signs ERC-712 typed data: the topic, the subject identity, the validity window, the scheme and the URI, and the payload. The wallet of the signer displays those fields, not an opaque hash.

Three properties follow from how the signature is built.

* **Bound to the subject.** The subject identity is part of what is signed. A claim cannot be copied to another identity.
* **Bound to the issuer.** The signing domain is the ONCHAINID of the issuer. The signature is only valid as a claim from that issuer.
* **Bound to its metadata.** The scheme and the URI are part of what is signed. Nobody can repoint a valid claim to a different document.

The signature is made by a key that holds `CLAIM_SIGNER` on the issuer's identity. That key can be any supported signer, including a passkey.

## How a claim reaches an identity

A claim is signed off-chain, then added to the subject identity. Adding is authorized in one of three ways.

| Path                                        | Who submits the claim                                | What authorizes the write                                                                                                            |
| ------------------------------------------- | ---------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------ |
| **The owner adds it**                       | A key of the subject identity calls `addClaim` on it | The key holds `CLAIM_SIGNER` or `CLAIM_ADDER` on the subject identity                                                                |
| **The issuer adds it, with a key grant**    | The issuer's identity, through `addClaimTo`          | The subject identity has granted the issuer's identity a `CLAIM_SIGNER` or `CLAIM_ADDER` key                                         |
| **The issuer adds it, as a trusted issuer** | The issuer's identity, through `addClaimTo`          | The issuer's identity is of type `CLAIM_ISSUER` and its reputation meets the network threshold. No grant from the subject is needed. |

A grant by the subject is the subject's own decision and is never overridden. The trusted issuer path applies only when there is no grant, and only to claims the issuer attributes to itself. An issuer can never write a claim in another issuer's name.

Whatever the path, the identity accepts a claim only if the issuer confirms, at that moment, that the claim is valid. An identity cannot be loaded with claims that their issuer does not stand behind.

```mermaid
sequenceDiagram
    participant INV as Investor
    participant CI as Claim Issuer
    participant CID as Claim Issuer ONCHAINID
    participant ID as Investor ONCHAINID

    INV->>CI: documents, off-chain
    CI->>CI: verify, build the claim, sign it with a CLAIM_SIGNER key
    CI->>CID: addClaimTo(topic, scheme, signature, data, uri, identity)
    CID->>CID: claim is valid for this issuer
    CID->>ID: addClaim(topic, scheme, issuer, signature, data, uri)
    ID->>ID: issuer holds a claim key here, or is a trusted issuer
    ID->>CID: isClaimValid(identity, topic, signature, data)
    CID-->>ID: true
    ID-->>INV: ClaimAdded
```

`addClaim`, `removeClaim` and `addClaimTo` are called directly on the identity by the key holder. A user operation of that identity, or a call it dispatches to itself, is refused. An issuer's identity can still call `addClaim` and `removeClaim` on another identity through its own execution flow. On the issuer's side, `addClaimTo` is called by a `MANAGEMENT` key of the issuer's identity: the key that signs claims and the key that submits them are distinct.

An identity can also hold a claim it issues about itself. It is signed like any other claim, by one of its own `CLAIM_SIGNER` keys.

## How validity is decided

Validity is decided by the issuer, every time it is asked. The register does not store a verdict. It calls `isClaimValid` on the issuer when it needs one, so the answer always reflects the present.

For an issuer that is an ONCHAINID, the checks run in this order, and `getClaimStatus` reports the first one that fails.

| Status         | Meaning                                                                       |
| -------------- | ----------------------------------------------------------------------------- |
| `NotYetValid`  | The current time is before `issuedAt`.                                        |
| `Expired`      | `validUntil` is set and has passed.                                           |
| `Revoked`      | The issuer has revoked this claim, or the claim was removed from an identity. |
| `NotIssued`    | The signer does not hold `CLAIM_SIGNER` on the issuer's identity.             |
| `BadSignature` | The signature is malformed or does not verify.                                |
| `Valid`        | None of the above.                                                            |

`isClaimValid` returns true only for `Valid`. `getClaimStatus` is for applications that need to tell a holder why a claim no longer counts.

## How a claim ends

```mermaid
stateDiagram-v2
    [*] --> Valid: added to the identity
    Valid --> Expired: validUntil passes
    Valid --> Revoked: the issuer revokes it
    Valid --> NotIssued: the signing key loses CLAIM_SIGNER
    Valid --> [*]: removed from the identity
```

| Event                            | Who acts                                                                                                    | Effect                                                                                                                 |
| -------------------------------- | ----------------------------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------- |
| **Expiry**                       | Nobody                                                                                                      | The claim stops being valid when `validUntil` passes. No transaction is needed.                                        |
| **Revocation**                   | The issuer, with a `MANAGEMENT` key of its identity, through `revokeClaimByDigest`                          | The claim stays stored on the subject identity and reads as `Revoked` from then on.                                    |
| **Removal**                      | A `CLAIM_SIGNER` key of the subject identity, or a trusted issuer for its own claims, through `removeClaim` | The claim is deleted from the subject identity and its digest is marked as spent.                                      |
| **Rotation of the signing key**  | The issuer, by removing `CLAIM_SIGNER` from a key                                                           | Every claim signed with that key stops being valid at once. This is how an issuer reacts to a compromised signing key. |
| **Loss of trust, for one asset** | The Issuer of the asset, by removing the Claim Issuer from its trusted issuers                              | The claim stays valid, and stops counting toward eligibility for that asset.                                           |

A `CLAIM_ADDER` key can add claims and cannot remove them.

Revocation and removal are final for the signed claim. A revoked or removed claim cannot be added again with the same signature. To attest the same fact again, the issuer signs a new claim.

Every one of these takes effect at the next eligibility check. Nothing has to be updated in any token or registry.

## Claim topics and their schemas

A topic is a number. What it means, and how its payload is structured, is a convention shared by the issuers that sign it and the Issuers that require it. The `IdentityUtilities` contract is an on-chain registry of those conventions: for each topic, a name and the names and types of the fields of its payload. Applications use it to decode and display claims, and to read an identity's claims with their schema in one call.

The registry describes topics. It plays no part in eligibility: the register checks that a valid claim exists for a topic, not what its payload says.

## Claims from other systems

The `issuer` of a claim does not have to be an ONCHAINID. It can be any contract that answers `isClaimValid`. This is how attestations that originate outside the protocol count toward eligibility: an adapter contract acts as the issuer and answers from the external system. The protocol ships one for the Ethereum Attestation Service, described in [External attestations](/identity-onchainid/external-attestations.md).

The register requires that an identity hold a valid claim of the required topic from an issuer the asset trusts. Where the underlying attestation comes from is a matter for that issuer.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation by asking a question.

Perform an HTTP GET request on the following URL with the `ask` and `goal` query parameters:

```
GET https://docs.t-rex.network/identity-onchainid/claims-issuance-validity-revocation.md?ask=<question>&goal=<user_goal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is what the user is ultimately trying to achieve, the reason they need the answer. Sharing it helps GitBook give you a better, more relevant answer. A goal is most helpful when it describes the outcome the user wants rather than restating the question. For example, with `ask=how do I create an API token`, a goal like `automate deployments from our CI pipeline` lets GitBook tailor the answer to that use case.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
