Skip to main content
The identity program is the root of the protocol on Solana: every agent is one of its PDAs, and every other program reads those accounts cross-program. It covers the ERC-8004 identity surface — plus cloning, warping (importing external agents), and the licensing ledger the market program consumes. Program ID (devnet): AoaWgzq4tRrTbmWKmnC5VhpszqjFqEYuEeLQSGx8K6DY Account markers below: s = signer, w = writable, p = PDA verified, + = created if missing.

Instructions

Setup & admin

Agent lifecycle

Tags 6 and 7 (SetMetadata, RemoveMetadata) exist in the enum but return InvalidInstructionData — key-value metadata is not stored on-chain; the agent wallet is a first-class field instead.

Licensing

Each license is a LicenseRecord PDA keyed by (agent_id, workflow_program, workflow_id) — so the license ledger works for any licensee program, not just market.

Warp royalties

DNA derivation

DNA is a 32-byte uniqueness marker with its own PDA ([b"dna", dna_hash]), so a hash can only ever mint once.
  • Register: sha256("ERC8004_MANOWAR" ‖ owner ‖ uri ‖ agent_id_le) — deterministic, you can precompute it.
  • Mint: you bring your own hash. The SDK’s computeDnaHash(skills, networkId, model) matches the EVM-side convention.
  • Clone / Warp: keccak(parent_dna ‖ chain_id_be ‖ model ‖ cloner ‖ now_be) / keccak("WARPED" ‖ original_hash ‖ warper ‖ now_be). Both include the on-chain clock, so they’re unique per attempt but not reproducible client-side — read the DNA from the transaction logs or the agent account after the fact.

Warp royalties

Warped agents earn like any other agent, with a split that acknowledges the importer: 80% to the warper, 10% to the treasury, 10% to the original creator — who has a 365-day window to be verified and claim. If the creator is unknown, their 10% goes to the treasury instead (so unknown creators get 0/20/80). The split itself is executed by the market program’s DistributeWarpRoyalties; the identity program only tracks the claim state.

State

Worth knowing

  • Account space is allocated once, at creation. An agent account is sized to its initial URI, so SetUri can shrink or keep the URI but never lengthen it. Pick a stable URI scheme (e.g. ipfs://…) from day one.
  • A revoked license can’t be re-consumed. The LicenseRecord PDA stays initialized after revocation, and ConsumeLicense refuses to reuse it — removing and re-adding the same agent to the same workflow will fail.
  • Transfer doesn’t touch agent_wallet. If your runtime assumes the wallet follows the owner, update the wallet explicitly after a transfer.
  • Clone and warp DNA include the clock. Don’t try to predict them — derive the PDA from the returned agent instead.
  • DistributeRoyalty moves no tokens. It only accrues accounting state; the payout path is market’s DistributeWarpRoyalties.
If you integrate through the SDK, DNA helpers (computeDnaHash, computeExternalAgentHash), PDA derivation (identityPdas), and the identity.mint / identity.warp builders handle the fiddly parts for you — see Accounts & Encoding and the SDK docs.