{"id":"ERC-7231","name":"Identity-Binding NFT","status":"Final","chain":"both","category":{"id":"identity","name":"Identity & Privacy","description":"Who you are on-chain, and what you choose to reveal"},"journeyStages":[{"id":"authentication","name":"Authentication & Identity","description":"Proving who you are and logging in"}],"uxImpact":"ERC-7231 binds a custom set of Web2/Web3 identity records to an NFT through an identitiesRoot and verifier-specific proof. Its required interface exposes setIdentitiesRoot, getIdentitiesRoot, and verifyIdentitiesBinding; it does not define add/remove identity methods or guarantee that the bound accounts belong to one real human.","officialUrl":"https://ercs.ethereum.org/ERCS/erc-7231","lastReviewed":"2026-09-18","lastUpdated":"2026-09-18","kind":"proposal","hasDetailedContent":true,"content":{"id":"ERC-7231","summary":"ERC-7231 binds a custom set of Web2/Web3 identity records to an NFT through an identitiesRoot and verifier-specific proof. Its required interface exposes setIdentitiesRoot, getIdentitiesRoot, and verifyIdentitiesBinding; it does not define add/remove identity methods or guarantee that the bound accounts belong to one real human.","applicability":{"whenToUse":["An NFT needs a root commitment for a custom set of Web2/Web3 identity records.","The verifier can check userIDs, identitiesRoot, owner address, and signature.","The product can distinguish identity binding from external authenticity or real-human policy."],"whenToAvoid":["The implementation does not expose the root and verifier methods or a verifier the app can use.","The product needs standardized add/remove identity calls; those belong to the selected implementation.","The UI cannot explain verifier-specific proofs and privacy choices."]},"designerTakeaways":["You can commit a custom identity bundle to an NFT and show its identitiesRoot.","You can verify userIDs with the configured verifier and show the proof scope.","You can separate account binding, verifier evidence, and any external human-authenticity policy."],"problemsSolved":[{"problem":"Identity records need a commitment tied to an NFT","oldWay":"An app stores a mutable list with no on-chain binding","newWay":"The implementation stores an identitiesRoot for the token","impact":"high"},{"problem":"Verifiers need to check an off-chain identity bundle","oldWay":"Each app invents its own proof format","newWay":"verifyIdentitiesBinding checks userIDs, root, owner address, and signature under the chosen verifier","impact":"high"},{"problem":"Identity updates need an explicit state transition","oldWay":"A UI silently replaces the list","newWay":"setIdentitiesRoot emits a root update that indexers can track","impact":"medium"},{"problem":"Users need to understand identity evidence","oldWay":"A “human verified” badge hides verifier policy","newWay":"Show userID, verifierUri, root, proof, and external authenticity policy separately","impact":"high"}],"uxPatterns":[{"name":"Identity Root Display","description":"Show the committed root and verifier context for the token.","userFlow":["User opens identity NFT","App reads getIdentitiesRoot(id)","Shows root and metadata version","Explains that individual records are verified through a proof"]},{"name":"Identity Binding Verification","description":"Verify a supplied identity list without implying personhood.","userFlow":["User chooses identities to inspect","App loads userID and verifierUri records","Calls verifyIdentitiesBinding with the root and signature","Shows proof result and verifier policy","Separates account binding from real-human claims"]},{"name":"Root Update History","description":"Make root changes and metadata versions visible.","userFlow":["Indexer observes SetIdentitiesRoot","App compares old and new roots","Shows version or changed state","Links to the current verifier URI"]}],"uiComponents":[{"name":"AccountConnector","description":"Display bound identities and verifier results.","states":["disconnected","connecting","connected","error"],"props":["platform","username","onConnect","onDisconnect"]},{"name":"IdentityRecordCard","description":"Display bound identity records and the selected verifier's proof result without implying a universal verification status.","states":["loading","records-loaded","partial","unknown"],"props":["nftId","accounts[]","lastUpdated","owner","verifierUri"]},{"name":"VerificationResultBadge","description":"Show the selected verifier's result for an identity record; do not imply universal identity verification.","states":["verified-by-verifier","pending","unknown","unverified"],"props":["platform","username","verifierUri","result"]},{"name":"IdentityRequirements","description":"List application-defined identity requirements for an access gate when the product defines one; the ERC does not define access policy.","states":["checking","met","unmet","partial","unknown"],"props":["requirements[]","userIdentity","verifier","onMeetRequirements"]}],"antiPatterns":[{"pattern":"Promising a real-human or Sybil-proof identity","why":"The standard commits identity data but leaves authenticity and verifier policy outside the required interface.","instead":"Name the verifier and describe what its proof establishes.","severity":"critical"},{"pattern":"Inventing add/remove identity methods","why":"The required interface stores and verifies a root; it does not define per-identity mutation.","instead":"Describe root replacement/versioning as implementation behavior.","severity":"critical"},{"pattern":"Showing all identities as public facts","why":"The metadata schema and verifier may use off-chain or privacy-preserving records.","instead":"Show the userID, verifier URI, disclosure, and proof scope explicitly.","severity":"high"}],"keyTakeaways":["ERC-7231 is a root commitment plus verifier-specific binding proof.","Use setIdentitiesRoot, getIdentitiesRoot, and verifyIdentitiesBinding.","Add/remove/version semantics belong to the chosen implementation.","Do not equate multiple bound identities with one real human."],"technicalNotes":"ERC-7231 requires setIdentitiesRoot(uint256 id, bytes32 identitiesRoot), getIdentitiesRoot(uint256 id), and verifyIdentitiesBinding(uint256 id, address nftOwnerAddress, string[] userIDs, bytes32 identitiesRoot, bytes signature). The metadata carries userID and verifierUri information, while authenticity, schema, privacy, and root update policy remain implementation/verifier choices.","lastUpdated":"2026-09-18","specConstraints":[{"id":"identity-verification-result","constraint":"The verification function returns true or false without modifying state.","appliesTo":"application","normativity":"normative","specQuote":"* MUST If the verification is passed, return true, otherwise return false","specSection":"Specification — Every compliant contract must implement the Interface","specUrl":"https://ercs.ethereum.org/ERCS/erc-7231#every-compliant-contract-must-implement-the-interface","designImplication":"Render verification as a current result, not as a state-changing transaction. Provide an explicit unknown or failed verification state."},{"id":"identity-erc721-compatibility","constraint":"The identity extension can remain fully ERC-721 compatible by adding its extension functions.","appliesTo":"application","normativity":"backwards-compatibility","specQuote":"## Backwards Compatibility\n\nAs mentioned in the specifications section, this standard can be fully [ERC-721](./eip-721.md) compatible by adding an extension function set.\nIn addition, new functions introduced in this standard have many similarities with the existing functions in [ERC-721](./eip-721.md). This allows developers to easily adopt the standard quickly.","specSection":"Backwards Compatibility","specUrl":"https://ercs.ethereum.org/ERCS/erc-7231#backwards-compatibility","designImplication":"Keep standard NFT ownership views and add identity verification as a separate layer."}],"sources":[{"label":"ERC-7231 official specification","url":"https://ercs.ethereum.org/ERCS/erc-7231","type":"official-spec"}],"lastReviewed":"2026-09-18"},"sources":[{"label":"Official specification","url":"https://ercs.ethereum.org/ERCS/erc-7231","type":"official-spec"},{"label":"Discussion search","url":"https://ethereum-magicians.org/search?q=ERC-7231","type":"discussion"}],"urls":{"canonical":"https://www.eipsfordesigners.com/standards/ERC-7231","markdown":"https://www.eipsfordesigners.com/standards/ERC-7231/content.md","agent":"https://www.eipsfordesigners.com/standards/ERC-7231/agent.md","api":"https://www.eipsfordesigners.com/api/standards/ERC-7231","official":"https://ercs.ethereum.org/ERCS/erc-7231","discussion":"https://ethereum-magicians.org/search?q=ERC-7231"},"freshness":{"lastReviewed":"2026-09-18","lastUpdated":"2026-09-18"}}