Introduction
Most DID methods treat resolution as a public operation: anyone with a DID string can look up the associated document. For many use cases, this is fine. For others, it's a fundamental privacy failure. If your DID document is publicly resolvable, every interaction that references your DID is linkable. did:btcr2 takes a different approach: DID documents are private by default, delivered through sidecars rather than published on public infrastructure.
The Problem with Public Resolution
Consider a typical publicly-resolvable DID:
- You present your DID to a verifier
- The verifier resolves it through a public network (ION nodes, a Universal Resolver, etc.)
- The verifier sees your full DID document: all your public keys, service endpoints, and metadata
This works for organizational DIDs that are meant to be public (a company's verification endpoint, a government's credential issuer DID). But for individuals, public resolution creates problems:
- Correlation: If you use the same DID with multiple verifiers, any of them (or any observer of the resolution network) can correlate your activities.
- Metadata leakage: Your DID document reveals what services you use, what key types you've configured, and how recently you've updated. This is a fingerprint.
- Surveillance: A resolution network that logs queries knows who is checking on whom.
btcr2's Sidecar Model
In btcr2, the DID document and its update history are not published to any public registry. Instead, they're delivered as a "sidecar": auxiliary data provided directly from the DID controller to the relying party.
How It Works
-
Genesis state: When a btcr2 DID is created, the genesis DID document exists only with the controller. For key-based DIDs (
kprefix), the genesis document can be deterministically reconstructed from the public key. For document-based DIDs (xprefix), the genesis document must be provided. -
Update history: Each update (a signed JSON Patch anchored to Bitcoin) is collected by the controller. The full chain of updates from genesis to current state forms the sidecar.
-
Presentation: When the controller wants to share their identity, they provide the DID string along with the sidecar data. The relying party can verify the entire history:
- Check each update's BIP340 Schnorr signature
- Confirm each update's hash matches its Bitcoin anchor
- Replay the JSON Patch operations to reconstruct the current document
-
Closed-loop resolution: The relying party resolves the DID using only the sidecar data and Bitcoin blockchain verification. No external resolution service is contacted.
What Goes On-Chain
Only opaque hashes appear on Bitcoin:
- Singleton beacons: the SHA-256 hash of the update
- CAS beacons: the hash of the Beacon Announcement Map
- SMT beacons: the Sparse Merkle Tree root
An observer scanning the Bitcoin blockchain sees transaction outputs with hash data. They cannot determine which DIDs were updated or what the updates contain. Aggregate beacons (CAS and SMT) further obscure how many DIDs a single transaction affects, since one Beacon Signal commits to a batch of updates. A Singleton beacon, by contrast, commits to a single update targeting one DID document, so an observer who recognizes it as a Singleton beacon can infer it affects one identity, though never which one (did:btcr2 spec, Beacons).
Privacy Properties
Non-Correlation by Default
Because there's no public resolution endpoint, two verifiers who receive the same DID can't discover this by querying a shared network. They each receive the sidecar independently. Unless they actively collude and compare notes, they don't know they're interacting with the same identity.
Pairwise DIDs at No Extra Cost
Since DID creation is free (offline, zero-cost), controllers can generate a unique DID for each relationship. Combined with private resolution, this means:
- Your employer knows you as
did:btcr2:k1abc... - Your bank knows you as
did:btcr2:k1def... - Neither can link the two identifiers
- Both can verify credentials issued to either DID (if you choose to present them)
Selective History Disclosure
The controller decides how much history to share. For a new relationship, providing only the current DID document state might suffice. For a high-trust interaction, the full history from genesis demonstrates continuity and non-tampering.
Resolution Modes
btcr2 supports a spectrum of resolution privacy:
Fully Private (Closed Loop)
- Sidecar delivered directly to the verifier
- No network resolution queries
- Maximum privacy, minimum infrastructure
Semi-Private (Trusted Resolver)
- Sidecar stored with a trusted service
- Verifier queries the service with the DID
- The service sees resolution requests, but only authorized verifiers can access it
Public (Open Resolution)
- DID document published to a publicly accessible endpoint
- Listed in the DID document's
servicesection - Appropriate for organizational DIDs meant to be discoverable
The controller chooses the mode per relationship. A single DID can be resolved privately by some parties and publicly by others.
Tradeoffs
Private resolution isn't free of tradeoffs:
- Sidecar management: The controller must maintain and deliver their update history. If the sidecar data is lost and no update has been anchored, the DID's current state can't be reconstructed by others.
- Larger payloads: Presenting a DID with its full sidecar history is more data than presenting a DID string alone. For long-lived, frequently-updated DIDs, the history grows.
- Offline verification dependency: The verifier needs the sidecar data at verification time. In scenarios where the controller isn't present to provide it, a cached or pre-delivered sidecar is required.
Conclusion
Privacy in decentralized identity isn't just about what credentials you present: it's about whether the identity infrastructure itself leaks information. btcr2's sidecar model ensures that the DID resolution process reveals nothing to the network. Combined with zero-cost pairwise DIDs and opaque on-chain anchors, it creates an identity system where privacy is structural, not bolted on.
