An AI Agent's Identity, Resolved On-Chain
Call ownerOf on it, and you get a wallet address. Call tokenURI, and that address unfolds into a did:solidus decentralized identifier. Resolve that DID against a completely different chain's public RPC, and it unfolds again into a full DID Document. Three calls, two networks, one identity, traced end to end below. Every value on this page was captured by re-running the calls just before publish, not copied from an earlier session.
The problem underneath the trace, in one sentence: an AI agent that isn't a person can't hold a passport or a driver's license, so today it mostly gets a wallet address or an API key, and neither tells a stranger who's accountable for what the agent does. What follows is one concrete answer to that, not a general theory of AI trust.
What ERC-8004 is
ERC-8004 ("Trustless Agents") is an Ethereum standard, formally proposed August 13, 2025 and co-authored by engineers from MetaMask, the Ethereum Foundation, Google, and Coinbase, with input from over 100 contributors. It defines three on-chain registries an autonomous agent can be anchored to, an Identity Registry (an ERC-721 "passport" NFT), a Reputation Registry, and a Validation Registry. Solidus didn't write any part of it and isn't claiming to; Solidus anchors real agents to the real Identity Registry contracts and builds the DID-and-credential layer the standard deliberately leaves open. Full attribution and the shipped/roadmap split live in the Lexicon: ERC-8004 and Agent Passport.
Step 1, the on-chain passport
Token 8064 lives at the ERC-8004 Identity Registry contract
0x8004A818BFB912233c491871b3d84c89A494BD9e, on Base Sepolia. Two read calls, no gas, no wallet
needed:
cast call 0x8004A818BFB912233c491871b3d84c89A494BD9e \
"ownerOf(uint256)(address)" 8064 \
--rpc-url https://base-sepolia-rpc.publicnode.com
0xcDCFA8a7709796E13bc8bd9D86d3523933e3ede4
cast call 0x8004A818BFB912233c491871b3d84c89A494BD9e \
"tokenURI(uint256)(string)" 8064 \
--rpc-url https://base-sepolia-rpc.publicnode.com
"https://agents.solidus.network/v1/agents/d7b2f0ed-a5ba-4c48-a3af-7c14e8070b20/card"
That's it for the Ethereum side: an owner address, and a pointer to a document.
Step 2, what the passport points to
Fetch the URI tokenURI returned:
curl https://agents.solidus.network/v1/agents/d7b2f0ed-a5ba-4c48-a3af-7c14e8070b20/card
The response is a SolidusAgentCard, Solidus's own manifest format, not an ERC-8004-defined shape,
naming the agent's decentralized identifier:
{
"type": "SolidusAgentCard",
"did": "did:solidus:testnet:46Hzv2Ek4MXwj1Kenvix4tWCPr1J",
"erc8004": {
"chainId": 84532,
"tokenId": "8064",
"identityRegistry": "0x8004A818BFB912233c491871b3d84c89A494BD9e",
"owner": "0xcDCFA8a7709796E13bc8bd9D86d3523933e3ede4"
}
}
One thing worth calling out honestly: the live card's didMethod.registryStatus field reads
"registered in the W3C DID Method Registry (w3c/did-extensions PR #713)." That matches reality,
did:solidus was registered on 2026-07-04. It did not always: this field previously described the
method as submitted and under review long after the registration had merged, and that lag is worth
remembering rather than deleting. Don't take a card's self-description as the last word on anything,
in either direction; that's exactly why step 3 checks the chain directly instead of trusting the
document.
Step 3: the DID resolves independently
The did field above is a normal did:solidus identifier. It resolves the same way any
did:solidus DID does, see 002, resolve a DID yourself
for the mechanic in full; an agent's identity isn't a special case, it's the identical RPC call
pointed at a different DID:
curl -X POST https://rpc.solidus.network \
-H "Content-Type: application/json" \
-d '{"jsonrpc":"2.0","method":"solidus_didResolve","params":["did:solidus:testnet:46Hzv2Ek4MXwj1Kenvix4tWCPr1J"],"id":1}'
{"jsonrpc":"2.0","id":1,"result":{
"id":"did:solidus:testnet:46Hzv2Ek4MXwj1Kenvix4tWCPr1J",
"controller":"did:solidus:testnet:46Hzv2Ek4MXwj1Kenvix4tWCPr1J",
"verification_method":[{"id":"did:solidus:testnet:46Hzv2Ek4MXwj1Kenvix4tWCPr1J#key-0",
"type":"Ed25519VerificationKey2020",
"publicKeyHex":"4ac407d14cab5627f69f0b3067a3cd6c340c610c3c414f367b3bdac1343c2044"}],
"active":true}}
No lookup against a private database, no trusting the agent's own claims about itself: the same public DID resolution endpoint anyone can hit for any did:solidus identifier answers back with a real key. The chain doesn't know or care that the DID it just resolved belongs to a piece of software instead of a person.
Why this matters
An autonomous agent making decisions or moving funds on someone's behalf raises an obvious question: who's accountable for it? Right now the field mostly answers that with a wallet address or an API key, neither tells a stranger anything about who's behind it. Chaining an ERC-8004 passport to a resolvable DID gives a different answer: a stranger interacting with the agent can look up who owns its passport and pull its identity document without asking the agent to vouch for itself, and without trusting a platform's private database that could disappear or lie. That's a narrow, concrete guarantee, a checkable identity that outlives any one platform, verifiable by anyone with a terminal, not a solved problem in AI trust generally, and not a claim that this makes an agent trustworthy in any deeper sense. It only makes the agent's owner findable.
What this isn't
One passport exists today, minted for testing, not a fleet of production agents.
For the fuller picture of what an agent identity is used for beyond this trace, credentials, capability scopes, the agent product itself, see agents.solidus.network.

