owned this note
owned this note
Published
Linked with GitHub
# Proposal for `did:dns` method specification
This document describes an alternative method (to the [existing spec](https://danubetech.github.io/did-method-dns/)) for using the DNS infrastructure to register DID documents.
## Motivation
The existing DNS infrastucture has many advantages for providing a robust DID document platform
- Compatible syntax, such that domains and subdomains are good candidates for DID identifiers that unambiguously identify the controller
- DNS lookup protocol can be used without modifications to resolve DID documents
- DNS storage using resource records can be used without modifications to store DID documents
- DNS security protocols can be used to provide authenticity, such as DNSSEC
- DNS caching and replication provide fast DID lookup
- Existing DNS lookup libraries and tools can be used to retrieve DID documents making the DID resolution easy and accessible to any language
## Comparison to `did:web`
`did:web` method is based on proving ownership of the web server by placing a file in a well known location. This then implies that the DID identifier, like `example.com`, will correctly point to the web server where this file is hosted. The `did:web` method assumes the DNS infrastructure is trusted and will always point to the correct web server.
`did:web` is built in the layer 7 OSI model.
In contrast, `did:dns` does not make any assumptions about existing trust and directly uses domain ownership as the root of trust. This means `did:dns` doesn't require other existing trusted entities in the domain space to resolve DID documents, since DNS servers are accessible by IP address. Therefore, at minimum, it only relies on layer 4 transport protocols (although layer 7 using DNS over HTTPS can be used for increased security).
`did:dns` does not support host paths like `did:web`.
## Cons
- Not able to use point in time resolution
- TTL propagation can be issue when doing key rotation
- DNS ownership transfer can impact historical VCs
## Specification
### Create DID operation
`did:dns`, as outlined in this document, uses TXT resource records to store the document data in the zone that matches the DID identifier. TXT records can be used to specify any metadata about the zone. A zone can contain multiple TXT records, which makes it good candidate to store almost any size of DID document.
The TXT records however have limits on the length of each record; this specification provides guidance how to work around this limitation.
Given an existing DID document for controller `did:dns:example.com`
```jsonld
{
"@context": [
"https://www.w3.org/ns/did/v1",
"https://w3id.org/security/suites/jws-2020/v1",
{ "@base": "did:dns:example.com" }
],
"id": "did:dns:example.com",
"verificationMethod": [
{
"id": "#key-1",
"controller": "did:dns:example.com",
"type": "JsonWebKey2020",
"publicKeyJwk": {
"kty": "OKP",
"crv": "Bls12381G2",
"x": "jORqtEunjFk8GVBbGb7R6PjADVVrRlCN97tOoVDvnUO0HjM_KkTTMJt2dacQwOXiFpViAp4zlL-BXhwUSM0mF1ZkBhmihGm_3WWrc_IS4bid3RJanKiM8ikC6Us-Rwt7"
}
}
],
"assertionMethod": [
"#key-1"
],
"authentication": [
"#key-1"
]
}
```
This document can be compacted using [JSON Canonicalization Scheme](https://www.rfc-editor.org/rfc/rfc8785) (JCS) and inserted into a TXT record under the zone `_did.<domain>`.
TXT records larger than 255 characters should be separated into strings of 255 characters. Most DNS providers do this automatically.
In cases when the DID document may be too large to store in a single TXT record, we can break down the document in smaller JSON objects that combined together will give the final document structure.
```json
{
"@context": [
"https://www.w3.org/ns/did/v1",
"https://w3id.org/security/suites/jws-2020/v1",
{ "@base": "did:dns:example.com" }
]
}
{ "id": "did:dns:example.com" }
{
"verificationMethod": [
{
"id": "#key-1",
"controller": "did:dns:example.com",
"type": "JsonWebKey2020",
"publicKeyJwk": {
"kty": "OKP",
"crv": "Bls12381G2",
"x": "jORqtEunjFk8GVBbGb7R6PjADVVrRlCN97tOoVDvnUO0HjM_KkTTMJt2dacQwOXiFpViAp4zlL-BXhwUSM0mF1ZkBhmihGm_3WWrc_IS4bid3RJanKiM8ikC6Us-Rwt7"
}
}
]
}
// multiple fields may be combined if they're short enough
{
"assertionMethod": [ "#key-1" ],
"authentication": [ "#key-1" ]
}
```
Each of these entries will be stored as a TXT record in the DNS zone with prefix `_did` (ex: `_did.example.com`). Each record may be serialized using JCS to keep things compact and small.
The final zone file for this document in BIND format will look like:
```txt
_did.example.trinsic.cloud. 300 IN TXT "{\"@context\":[\"https://www.w3.org/ns/did/v1\",\"https://w3id.org/security/suites/jws-2020/v1\",{\"@base\":\"did:dns:example.trinsic.cloud\"}]}"
_did.example.trinsic.cloud. 300 IN TXT "{\"assertionMethod\":[\"#key-1\"],\"authentication\":[\"#key-1\"]}"
_did.example.trinsic.cloud. 300 IN TXT "{\"id\":\"did:dns:example.trinsic.cloud\"}"
_did.example.trinsic.cloud. 300 IN TXT "{\"verificationMethod\":[{\"id\":\"#key-1\",\"controller\":\"did:dns:example.trinsic.cloud\",\"type\":\"JsonWebKey2020\",\"publicKeyJwk\":{\"kty\":\"OKP\",\"crv\":\"Bls12381G2\",\"x\":\"jORqtEunjFk8GVBbGb7R6PjADVVrRlCN97tOoVDvnUO0HjM_KkTTMJt2dacQwOXiFpViAp4zlL-BXhwUSM0mF1ZkBhmihGm_" "3WWrc_IS4bid3RJanKiM8ikC6Us-Rwt7\"}}]}"
```
On TXT record limits:
> A TXT record contains one or more strings that are enclosed in double quotation marks ("). You can enter a value of up to 255 characters in one string in a TXT record. You can add multiple strings of 255 characters in a single TXT record. The maximum length of a value in a TXT record is 4,000 characters.
Different providers have different limits for TXT item size. The smallest I've encountered is Cloudflare with 2000 char limit.
#### An alternative representation using CBOR
This is just for consideration purposes. CBOR may be used to encode the individual objects instead JSON, which would potentially produce smaller size records.
#### An alternative representation using RDF
This is just for consideration purposes. Instead deconstructing the DID document into smaller JSON documents, the DID document can be serialized into RDF N-Triples and have each statement stored as TXT records instead. The downside to this approach is the requirement to use RDF and/or JSON-LD tooling to reconstruct the original document, while JSON tooling is much simpler and more available.
```
<did:dns:example.com#key-1> <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <https://w3id.org/security#JsonWebKey2020> .
<did:dns:example.com#key-1> <https://w3id.org/security#controller> <did:dns:example.com> .
<did:dns:example.com#key-1> <https://w3id.org/security#publicKeyJwk> "{\"crv\":\"Bls12381G2\",\"kty\":\"OKP\",\"x\":\"jORqtEunjFk8GVBbGb7R6PjADVVrRlCN97tOoVDvnUO0HjM_KkTTMJt2dacQwOXiFpViAp4zlL-BXhwUSM0mF1ZkBhmihGm_3WWrc_IS4bid3RJanKiM8ikC6Us-Rwt7\"}"^^<http://www.w3.org/1999/02/22-rdf-syntax-ns#JSON> .
<did:dns:example.com> <https://w3id.org/security#assertionMethod> <did:dns:example.com#key-1> .
<did:dns:example.com> <https://w3id.org/security#authenticationMethod> <did:dns:example.com#key-1> .
<did:dns:example.com> <https://w3id.org/security#verificationMethod> <did:dns:example.com#key-1> .
```
### Resolve DID operation
The process of DID document resolution consists of querying the DNS server for all TXT records and reconstructing the original DID document by merging the individual JSON entries.
For example, to resolve `did:dns:example.trinsic.cloud`, query the zone `_did.example.trinsic.cloud` for TXT records. Using the `dig` tool we can run the command:
```bash
dig +noall +answer -t txt _did.example.trinsic.cloud
# below zone contains larger DID document with multiple verification methods
# to showcase storing different sizes of TXT records that span multiple strings
dig +noall +answer -t txt _did.trinsic.cloud
```
Each of the zone records can then be merged into a single JSON document using any JSON processing method.
### Update and Delete DID operation
This operations involve updating or deleting TXT records from the DNS server.
### Encoding
```
type=json;seq=0;payload=<data payload>
type=cbor;seq=1;payload=<data payload>;v=1
```