Building a W3C-Compliant DID Method on Cardano — Architecture Decisions & Lessons Learned

Hey everyone,

I’m JW from Plausible Potentials (@PlausiblePotentials), a Cardano-first development agency based in Houston. We’ve been building cooperative infrastructure on Cardano for a while now and wanted to start sharing some of our architecture decisions and lessons learned with the community. This is the first in a series of technical posts — not a pitch, just a builder sharing field notes. Feedback and pushback are genuinely welcome.


What We Built

The C3 DID Method Specification — a W3C DID-compliant decentralized identity standard built natively on Cardano. The spec is live at did.c3-alliance.org.

The method identifier is did:c3 and the full DID format is:

did:c3:SEID:@P/D/T<hash>

This supports three distinct entity types:

  • @P (Persona) — Human members / natural persons
  • @D (DACO) — Decentralized Autonomous Cooperative Organizations (our institutional model)
  • @T (Tool) — Credentialed autonomous agents and tools (including AI agents)

The @T entity type is worth highlighting because it allows non-human agents to hold verifiable DIDs. We use this to credential an AI assistant (CoCoA) that acts on behalf of cooperative members. When CoCoA performs an action — casting a governance vote, submitting a marketplace bid — that action is cryptographically attributable to a verified tool operating under a verified persona’s delegated authority. More on CoCoA in a future post.


Why We Chose BLAKE2b-512 for SEID Generation

The Sovereign Entity Identifier (SEID) is the unique identifier component within each DID. We generate SEIDs using BLAKE2b-512.

Why BLAKE2b?

This was a straightforward decision for a Cardano-native implementation. BLAKE2b is already deeply embedded in Cardano’s cryptographic infrastructure — it’s used for address derivation, transaction hashing, and script validation across the protocol. Using BLAKE2b for SEID generation means we’re not introducing an additional cryptographic dependency into the stack. One less library. One less attack surface. One less thing to audit.

Why 512 specifically?

We went with the full 512-bit output rather than the 224 or 256 variants used elsewhere in Cardano. The reasoning was future-proofing. The SEID needs to remain collision-resistant across three entity types that may scale to millions of identifiers over decades. The additional bit-space was cheap insurance. We also wanted the full entropy spread for downstream key derivation operations — the SEID serves as the root from which entity-specific key material can be deterministically derived.

Trade-off acknowledged: The 512-bit output is longer than strictly necessary for collision resistance at current scale. We accepted the modest storage overhead in exchange for the entropy headroom. If we were optimizing purely for on-chain storage cost, BLAKE2b-256 would have been defensible. We chose to optimize for longevity over byte-efficiency.


The Three Entity Types — Design Rationale

Most DID methods treat all subjects as equivalent. A did:web or did:key doesn’t structurally distinguish between a person, an organization, and an autonomous tool. We found this insufficient for our use case.

The problem: In a cooperative economy, the relationship between a human member, the cooperative organization they belong to, and the tools that act on their behalf is not flat. These are structurally different entity types with different capability profiles, different governance rights, and different trust models. A Persona can delegate authority. A DACO can define governance rules. A Tool can execute delegated actions but cannot self-authorize.

Encoding the entity type directly into the DID syntax (@P, @D, @T) means that any system resolving a C3 DID can immediately determine what kind of entity it’s dealing with before resolving the full DID document. This is a parsing-level optimization that avoids a round-trip to the DID document just to determine entity classification.

Alternative considered: We could have stored entity type purely as metadata within the DID document rather than encoding it in the identifier itself. We rejected this because it would have required full DID resolution before even basic entity classification — an unnecessary network call for what should be a syntactic check.


Integration with Hyperledger Identus

The C3 DID Method integrates with Hyperledger Identus (formerly Atala PRISM) for verifiable credential issuance and management.

How this works in practice:

Identus handles the credential lifecycle — issuance, revocation, verification — while the C3 DID Method provides the identity anchoring layer. When a cooperative member earns an XPT (Experience Token) verified credential, Identus issues the credential, and the C3 DID is the subject identifier.

This separation of concerns was deliberate. We didn’t want to rebuild credential infrastructure that Identus already handles well. What Identus doesn’t provide out of the box is the cooperative-specific identity semantics — the three entity types, the SEID generation logic, the delegation model between Personas and Tools. The C3 DID Method fills that gap.

A use case Identus probably didn’t anticipate: We use XPT verified credentials as training data for a sovereign AI assistant. The verified credentials issued through Identus become the data substrate that the AI learns from — every piece of training data has cryptographic provenance through the Identus credential chain. This gives us verifiable AI training data, which as far as we can tell is a first. But that deserves its own post.


Sovereign Vault Integration (Lace.io)

DID documents and associated credentials are stored in the member’s Sovereign Vault via Lace.io integration. This means the identity data lives under the member’s direct control — not on our servers, not on a shared registry, not in a corporate database.

The design principle here is simple: if you’re building a decentralized identity system and the identity data lives on a centralized server, you haven’t actually decentralized identity. You’ve just moved the centralization point. Lace integration ensures that DID documents, credential stores, and delegation records all live in the same sovereignty boundary as the member’s other Cardano assets.


Lessons Learned

1. W3C DID Core compliance is harder than it looks. The spec is well-written but the conformance requirements have edge cases that only surface during implementation. Service endpoint registration, key rotation procedures, and deactivation semantics all required more design iteration than we initially estimated.

2. Entity type encoding in the DID syntax was the right call. Every system that consumes C3 DIDs benefits from being able to classify entity types at the string-parsing level. If we’d buried this in the DID document, every consumer would need full resolution before making basic routing decisions.

3. BLAKE2b-512 aligns well with Cardano’s existing cryptographic choices. Not having to introduce SHA-256 or Keccak into a Cardano-native stack eliminated an entire class of dependency management headaches. When your chain already uses BLAKE2b everywhere, use BLAKE2b.

4. Identus integration is smoother than expected. The Hyperledger Identus team has done solid work on the credential lifecycle APIs. The main gap we filled was cooperative-specific identity semantics, not plumbing.

5. The @T (Tool) entity type opened doors we didn’t fully anticipate. Once autonomous agents have their own DIDs, the design space for credentialed delegation, verifiable agent actions, and sovereign AI becomes tractable. This single design decision has had more downstream architectural impact than any other.


What We’re Looking For

Genuinely interested in feedback from the Cardano developer community on a few things:

  • SEID generation: Anyone see issues with the BLAKE2b-512 choice? Would you have made a different hashing decision for a Cardano-native DID method?
  • Entity type encoding: Thoughts on encoding @P/@D/@T in the DID syntax vs. keeping it purely in the DID document metadata?
  • Identus integration patterns: Anyone else building on Identus who’s found interesting integration approaches?
  • CIP alignment: We’ve been looking at CIP-0026 (off-chain metadata), CIP-0008 (message signing), and CIP-0100 (governance metadata) for alignment points. Any CIPs we should be paying closer attention to?

Links

This is the first in a series of technical posts. Next up: deploying Hydra in production for C3DEX — what worked, what didn’t, and what we wish we’d known.

Happy to answer questions or dig deeper into any of the architecture decisions.

— JW

1 Like

Yes… the CIP we are hoping you will write about your DID specification above (and on your GitHub repo: but with the promotional language filtered out). :star_struck: Other than that…

Maybe most importantly, in terms of cooperative standards: I think the Cardano community would like to hear whether your proposed platform will be compatible with Veridian (the wallet itself and/or KERI identifiers) vs. competitive or “winner take all” if there is any practical divergence: