Decentralized Identifier (DID) Resolution and DID URL Dereferencing v1.0

Algorithms and guidelines for resolving DIDs and dereferencing DID URLs

W3C First Public Working Draft

More details about this document
This version:
https://www.w3.org/TR/2024/WD-did-resolution-20241128/
Latest published version:
https://www.w3.org/TR/did-resolution/
Latest editor's draft:
https://w3c.github.io/did-resolution/
History:
https://www.w3.org/standards/history/did-resolution/
Commit history
Editors:
Markus Sabadello (Danube Tech)
Dmitri Zagidulin (MIT CSAIL)
Authors:
Markus Sabadello (Danube Tech)
Dmitri Zagidulin (MIT CSAIL)
Feedback:
GitHub w3c/did-resolution (pull requests, new issue, open issues)
public-did-wg@w3.org with subject line [did-resolution] … message topic … (archives)

Abstract

Decentralized identifiers (DIDs) are a new type of identifier for verifiable, "self-sovereign" digital identity. DIDs are fully under the control of the DID controller, independent from any centralized registry, identity provider, or certificate authority. DIDs resolve to DID Documents — simple documents that describe how to use that specific DID.

This document specifies the algorithms and guidelines for resolving DIDs and dereferencing DID URLs.

Status of This Document

This section describes the status of this document at the time of its publication. A list of current W3C publications and the latest revision of this technical report can be found in the W3C technical reports index at https://www.w3.org/TR/.

Comments regarding this document are welcome. Please file issues directly on GitHub, or send them to public-credentials@w3.org (subscribe, archives).

Portions of the work on this specification have been funded by the United States Department of Homeland Security's Science and Technology Directorate under contracts HSHQDC-17-C-00019. The content of this specification does not necessarily reflect the position or the policy of the U.S. Government and no official endorsement should be inferred.

Work on this specification has also been supported by the Rebooting the Web of Trust community facilitated by Christopher Allen, Shannon Appelcline, Kiara Robles, Brian Weller, Betty Dhamers, Kaliya Young, Kim Hamilton Duffy, Manu Sporny, Drummond Reed, Joe Andrieu, and Heather Vescent.

This document was published by the Decentralized Identifier Working Group as a First Public Working Draft using the Recommendation track.

Publication as a First Public Working Draft does not imply endorsement by W3C and its Members.

This is a draft document and may be updated, replaced or obsoleted by other documents at any time. It is inappropriate to cite this document as other than work in progress.

This document was produced by a group operating under the W3C Patent Policy. W3C maintains a public list of any patent disclosures made in connection with the deliverables of the group; that page also includes instructions for disclosing a patent. An individual who has actual knowledge of a patent which the individual believes contains Essential Claim(s) must disclose the information in accordance with section 6 of the W3C Patent Policy.

This document is governed by the 03 November 2023 W3C Process Document.

1. Introduction

DID resolution is the process of obtaining a DID document for a given DID. This is one of four required operations that can be performed on any DID ("Read"; the other ones being "Create", "Update", and "Deactivate"). The details of these operations differ depending on the DID method. Building on top of DID resolution, DID URL dereferencing is the process of retrieving a representation of a resource for a given DID URL. Software and/or hardware that is able to execute these processes is called a DID resolver.

This specification defines common requirements, algorithms including their inputs and results, architectural options, and various considerations for the DID resolution and DID URL dereferencing processes.

Note that while this specification defines some base-level functionality for DID resolution, the actual steps required to communicate with a DID's verifiable data registry are defined by the applicable DID method specification.

Note

The difference between "resolving" a DID and "dereferencing" a DID URL is being thoroughly discussed by the community. For example, see this comment.

1.1 Conformance

As well as sections marked as non-normative, all authoring guidelines, diagrams, examples, and notes in this specification are non-normative. Everything else in this specification is normative.

The key words MAY, MUST, MUST NOT, OPTIONAL, RECOMMENDED, REQUIRED, and SHOULD in this document are to be interpreted as described in BCP 14 [RFC2119] [RFC8174] when, and only when, they appear in all capitals, as shown here.

A conforming DID resolver is any algorithm realized as software and/or hardware that complies with the relevant normative statements in 3. DID Resolution.

A conforming DID URL dereferencer is any algorithm realized as software and/or hardware that complies with the relevant normative statements in 4. DID URL Dereferencing.

2. Terminology

This section defines the terms used in this specification and throughout decentralized identifier infrastructure. A link to these terms is included whenever they appear in this specification.

authenticate
Authentication is a process by which an entity can prove it has a specific attribute or controls a specific secret using one or more verification methods. With DIDs, a common example would be proving control of the cryptographic private key associated with a public key published in a DID document.
binding
A concrete mechanism through which a client invokes a DID resolver. This could be a local binding such as a local command line tool or library API, or a remote binding such as the HTTP(S) binding. See Section 6.2 Resolver Architectures.
client
Software and/or hardware that invokes a DID resolver in order to execute the DID resolution and/or DID URL dereferencing algorithms. This invocation is done via a binding. The term client does not imply any specific network topology.
decentralized identifier (DID)
A globally unique persistent identifier that does not require a centralized registration authority and is often generated and/or registered cryptographically. The generic format of a DID is defined in . A specific DID scheme is defined in a DID method specification. Many—but not all—DID methods make use of distributed ledger technology (DLT) or some other form of decentralized network.
DID controller
An entity that has the capability to make changes to a DID document. A DID might have more than one DID controller. The DID controller(s) can be denoted by the optional controller property at the top level of the DID document. Note that a DID controller might be the DID subject.
DID delegate
An entity to whom a DID controller has granted permission to use a verification method associated with a DID via a DID document. For example, a parent who controls a child's DID document might permit the child to use their personal device in order to authenticate. In this case, the child is the DID delegate. The child's personal device would contain the private cryptographic material enabling the child to authenticate using the DID. However, the child might not be permitted to add other personal devices without the parent's permission.
DID document
A set of data describing the DID subject, including mechanisms, such as cryptographic public keys, that the DID subject or a DID delegate can use to authenticate itself and prove its association with the DID.
DID fragment
The portion of a DID URL that follows the first hash sign character (#). DID fragment syntax is identical to URI fragment syntax.
DID method
A definition of how a specific DID method scheme is implemented. A DID method is defined by a DID method specification, which specifies the precise operations by which DIDs and DID documents are created, resolved, updated, and deactivated. See .
DID path
The portion of a DID URL that begins with and includes the first forward slash (/) character and ends with either a question mark (?) character, a fragment hash sign (#) character, or the end of the DID URL. DID path syntax is identical to URI path syntax. See .
DID query
The portion of a DID URL that follows and includes the first question mark character (?). DID query syntax is identical to URI query syntax. See .
DID resolution
The process that takes as its input a DID and a set of resolution options and returns a DID document in a conforming representation plus additional metadata. This process relies on the "Read" operation of the applicable DID method. The inputs and outputs of this process are defined in 3. DID Resolution.
DID resolver
A DID resolver is a software and/or hardware component that performs the DID resolution function by taking a DID as input and producing a conforming DID document as output.
DID resolution result
A data structure that represents the result of the DID resolution algorithm. May contain a DID document. See Section 7. DID Resolution Result.
DID scheme
The formal syntax of a decentralized identifier. The generic DID scheme begins with the prefix did: as defined in . Each DID method specification defines a specific DID method scheme that works with that specific DID method. In a specific DID method scheme, the DID method name follows the first colon and terminates with the second colon, e.g., did:example:
DID subject
The entity identified by a DID and described by a DID document. Anything can be a DID subject: person, group, organization, physical thing, digital thing, logical thing, etc.
DID URL
A DID plus any additional syntactic component that conforms to the definition in . This includes an optional DID path (with its leading / character), optional DID query (with its leading ? character), and optional DID fragment (with its leading # character).
DID URL dereferencing
The process that takes as its input a DID URL and a set of input metadata, and returns a resource. This resource might be a DID document plus additional metadata, a secondary resource contained within the DID document, or a resource entirely external to the DID document. The process uses DID resolution to fetch a DID document indicated by the DID contained within the DID URL. The dereferencing process can then perform additional processing on the DID document to return the dereferenced resource indicated by the DID URL. The inputs and outputs of this process are defined in 4. DID URL Dereferencing.
DID URL dereferencer
A software and/or hardware system that performs the DID URL dereferencing function for a given DID URL or DID document.
DID URL dereferencing result
A data structure that represents the result of the DID URL dereferencing algorithm. May contain a DID document or other content. See Section 8. DID URL Dereferencing Result.
distributed ledger (DLT)
A non-centralized system for recording events. These systems establish sufficient confidence for participants to rely upon the data recorded by others to make operational decisions. They typically use distributed databases where different nodes use a consensus protocol to confirm the ordering of cryptographically signed transactions. The linking of digitally signed transactions over time often makes the history of the ledger effectively immutable.
resource
As defined by [RFC3986]: "...the term 'resource' is used in a general sense for whatever might be identified by a URI." Similarly, any resource might serve as a DID subject identified by a DID.
representation
As defined for HTTP by [RFC7231]: "information that is intended to reflect a past, current, or desired state of a given resource, in a format that can be readily communicated via the protocol, and that consists of a set of representation metadata and a potentially unbounded stream of representation data." A DID document is a representation of information describing a DID subject. See .
local binding
A binding where the client invokes a DID resolver that runs on the same network host, e.g., via a local command line tool or library API. In this case, the DID resolver is sometimes also called a "local DID resolver". See Section 6.2 Resolver Architectures.
remote binding
A binding where the client invokes a DID resolver that runs on a different network host, e.g., via the HTTP(S) binding. In this case, the DID resolver is sometimes also called a "remote DID resolver". See Section 6.2 Resolver Architectures.
services
Means of communicating or interacting with the DID subject or associated entities via one or more service endpoints. Examples include discovery services, agent services, social networking services, file storage services, and verifiable credential repository services.
service endpoint
A network address, such as an HTTP URL, at which services operate on behalf of a DID subject.
service endpoint construction
An algorithm that takes a DID URL and a service, and constructs a service endpoint URL See Section 11. Service Endpoint Construction.
unverifiable read
A low confidence implementation of a DID method's "Read" operation between the DID resolver and the verifiable data registry, to obtain the DID document. There is no guarantee about the integrity and correctness of the result. See Section 6.1 Method Architectures.
verifiable data registry
A system that facilitates the creation, verification, updating, and/or deactivation of decentralized identifiers and DID documents. A verifiable data registry might also be used for other cryptographically-verifiable data structures such as verifiable credentials. For more information, see the W3C Verifiable Credentials specification [VC-DATA-MODEL].
verification method

A set of parameters that can be used together with a process to independently verify a proof. For example, a cryptographic public key can be used as a verification method with respect to a digital signature; in such usage, it verifies that the signer possessed the associated cryptographic private key.

"Verification" and "proof" in this definition are intended to apply broadly. For example, a cryptographic public key might be used during Diffie-Hellman key exchange to negotiate a shared symmetric key for encryption. This guarantees the integrity of the key agreement process. It is thus another type of verification method, even though descriptions of the process might not use the words "verification" or "proof."

verifiable read
A high confidence implementation of a DID method's "Read" operation between the DID resolver and the verifiable data registry, to obtain the DID document. There are guarantees about the integrity and correctness of the result to the extent possible under the applicable DID method. See Section 6.1 Method Architectures.

3. DID Resolution

The DID resolution functions resolve a DID into a DID document by using the "Read" operation of the applicable DID method as described in Method Operations. All conforming DID resolvers implement the functions below, which have the following abstract forms:

resolve(did, resolutionOptions) →
   « didResolutionMetadata, didDocument, didDocumentMetadata »

resolveRepresentation(did, resolutionOptions) →
   « didResolutionMetadata, didDocumentStream, didDocumentMetadata »

The resolve function returns the DID document in its abstract form (a map). The resolveRepresentation function returns a byte stream of the DID Document formatted in the corresponding representation.


Diagram illustrating how resolve() returns the DID document data model in
its abstract form and resolveRepresenation() returns it in one of the
conformant representations; conversion is possible using production and
consumption rules.
Figure 1 Functions resolve() and resolveRepresentation(). See also: narrative description.

The upper middle part of the diagram contains a rectangle with dashed grey outline, containing two blue-outlined rectangles, one above the other. The upper, larger rectangle is labeled, in blue, "Core Properties", and contains the following INFRA notation:

«[
  "id""example:123",
  "verificationMethod" → « «[
    "id": "did:example:123#keys-1",
    "controller": "did:example:123",
    "type": "Ed25519VerificationKey2018",
    "publicKeyBase58": "H3C2AVvLMv6gmMNam3uVA"
  ]» »,
  "authentication" → «
    "did:example:123#keys-1"
  »
]»

The lower, smaller rectangle is labeled, in blue, "Core Representation-specific Entries (JSON-LD)", and contains the following monospaced INFRA notation:

«[ "@context""https://www.w3.org/ns/did/v1" ]»

From the grey-outlined rectangle, three pairs of arrows extend to three different black-outlined rectangles, aligned in a horizontal row side-by-side, in the bottom half of the diagram. Each pair of arrows consists of one blue arrow pointing from the grey-outlined rectangle to the respective black-outlined rectangle, labeled "produce", and one red arrow pointing in the reverse direction, labeled "consume". The first black-outlined rectangle in the row is labeled "application/did+ld+json", and contains the following JSON-LD data:

{
  "@context": ["https://www.w3.org/ns/did/v1"],
  "id": "did:example:123",
  "verificationMethod": [{
    "id": "did:example:123#keys-1",
    "controller": "did:example:123",
    "type": "Ed25519VerificationKey2018",
    "publicKeyBase58": "H3C2AVvLMv6gmMNam3uVA"
  }],
  "authentication": [
    "did:example:123#keys-1"
  ]
}

The second rectangle in the row is labeled "application/did+json" and contains the following JSON data:

{
  "id": "did:example:123",
  "verificationMethod": [{
    "id": "did:example:123#keys-1",
    "controller": "did:example:123",
    "type": "Ed25519VerificationKey2018",
    "publicKeyBase58": "H3C2AVvLMv6gmMNam3uVA"
  }],
  "authentication": [
    "did:example:123#keys-1"
  ]
}

The third rectangle in the row is labeled "application/did+cbor", and contains hexadecimal data.

In the left part of the diagram, in the middle, there is a box, with black outline and light gray background. This box is labeled "VERIFIABLE DATA REGISTRY" and contains a symbol representing a graph with nodes and arcs. From this box, one arrow, labeled "resolve()", extends upwards and points to the top half of the diagram where the grey-outlined rectangle is located. Another arrow, labeled "resolveRepresentation()", extends downwards and points to the bottom half of the diagram, where the row of three black-outlined rectangles is located.

All conformant DID resolvers MUST implement the DID resolution functions for at least one DID method and MUST be able to return a DID document in at least one conformant representation.

Conforming DID resolver implementations do not alter the signature of these functions in any way. DID resolver implementations might map the resolve and resolveRepresentation functions to a method-specific internal function to perform the actual DID resolution process. DID resolver implementations might implement and expose additional functions with different signatures in addition to the resolve and resolveRepresentation functions specified here.

The input variables of the resolve and resolveRepresentation functions are as follows:

did
This is the DID to resolve. This input is REQUIRED and the value MUST be a conformant DID as defined in .
resolutionOptions
A metadata structure containing properties defined in 3.1 DID Resolution Options. This input is REQUIRED, but the structure MAY be empty.

These functions each return multiple values, and no limitations are placed on how these values are returned together. The return values of resolve are didResolutionMetadata, didDocument, and didDocumentMetadata. The return values of resolveRepresentation are didResolutionMetadata, didDocumentStream, and didDocumentMetadata. These values are described below:

didResolutionMetadata
A metadata structure consisting of values relating to the results of the DID resolution process which typically changes between invocations of the resolve and resolveRepresentation functions, as it represents data about the resolution process itself. This structure is REQUIRED, and in the case of an error in the resolution process, this MUST NOT be empty. This metadata is defined by 3.2 DID Resolution Metadata. If resolveRepresentation was called, this structure MUST contain a contentType property containing the Media Type of the representation found in the didDocumentStream. If the resolution is not successful, this structure MUST contain an error property describing the error.
didDocument
If the resolution is successful, and if the resolve function was called, this MUST be a DID document abstract data model (a map) as described in that is capable of being transformed into a conforming DID Document (representation), using the production rules specified by the representation. The value of id in the resolved DID document MUST match the DID that was resolved. If the resolution is unsuccessful, this value MUST be empty.
didDocumentStream
If the resolution is successful, and if the resolveRepresentation function was called, this MUST be a byte stream of the resolved DID document in one of the conformant representations. The byte stream might then be parsed by the caller of the resolveRepresentation function into a data model, which can in turn be validated and processed. If the resolution is unsuccessful, this value MUST be an empty stream.
didDocumentMetadata
If the resolution is successful, this MUST be a metadata structure. This structure contains metadata about the DID document contained in the didDocument property. This metadata typically does not change between invocations of the resolve and resolveRepresentation functions unless the DID document changes, as it represents metadata about the DID document. If the resolution is unsuccessful, this output MUST be an empty metadata structure. Properties defined by this specification are in 3.3 DID Document Metadata.

3.1 DID Resolution Options

The possible properties within this structure and their possible values are registered in the DID Specification Registries [DID-SPEC-REGISTRIES]. This specification defines the following common properties.

accept
The Media Type of the caller's preferred representation of the DID document. The Media Type MUST be expressed as an ASCII string. The DID resolver implementation SHOULD use this value to determine the representation contained in the returned didDocumentStream if such a representation is supported and available. This property is OPTIONAL for the resolveRepresentation function and MUST NOT be used with the resolve function.

3.2 DID Resolution Metadata

The possible properties within this structure and their possible values are registered in the DID Specification Registries [DID-SPEC-REGISTRIES]. This specification defines the following DID resolution metadata properties:

contentType
The Media Type of the returned didDocumentStream. This property is REQUIRED if resolution is successful and if the resolveRepresentation function was called. This property MUST NOT be present if the resolve function was called. The value of this property MUST be an ASCII string that is the Media Type of the conformant representations. The caller of the resolveRepresentation function MUST use this value when determining how to parse and process the didDocumentStream returned by this function into the data model.
error
The error code from the resolution process. This property is REQUIRED when there is an error in the resolution process. The value of this property MUST be a single keyword ASCII string. The possible property values of this field SHOULD be registered in the DID Specification Registries [DID-SPEC-REGISTRIES]. This specification defines the following common error values:
invalidDid
The DID supplied to the DID resolution function does not conform to valid syntax. (See .)
notFound
The DID resolver was unable to find the DID document resulting from this resolution request.
representationNotSupported
This error code is returned if the representation requested via the accept input metadata property is not supported by the DID method and/or DID resolver implementation.

3.3 DID Document Metadata

The possible properties within this structure and their possible values SHOULD be registered in the DID Specification Registries [DID-SPEC-REGISTRIES]. This specification defines the following common properties.

created
DID document metadata SHOULD include a created property to indicate the timestamp of the Create operation. The value of the property MUST be a string formatted as an XML Datetime normalized to UTC 00:00:00 and without sub-second decimal precision. For example: 2020-12-20T19:17:47Z.
updated
DID document metadata SHOULD include an updated property to indicate the timestamp of the last Update operation for the document version which was resolved. The value of the property MUST follow the same formatting rules as the created property. The updated property is omitted if an Update operation has never been performed on the DID document. If an updated property exists, it can be the same value as the created property when the difference between the two timestamps is less than one second.
deactivated
If a DID has been deactivated, DID document metadata MUST include this property with the boolean value true. If a DID has not been deactivated, this property is OPTIONAL, but if included, MUST have the boolean value false.
nextUpdate
DID document metadata MAY include a nextUpdate property if the resolved document version is not the latest version of the document. It indicates the timestamp of the next Update operation. The value of the property MUST follow the same formatting rules as the created property.
versionId
DID document metadata SHOULD include a versionId property to indicate the version of the last Update operation for the document version which was resolved. The value of the property MUST be an ASCII string.
nextVersionId
DID document metadata MAY include a nextVersionId property if the resolved document version is not the latest version of the document. It indicates the version of the next Update operation. The value of the property MUST be an ASCII string.
equivalentId

A DID method can define different forms of a DID that are logically equivalent. An example is when a DID takes one form prior to registration in a verifiable data registry and another form after such registration. In this case, the DID method specification might need to express one or more DIDs that are logically equivalent to the resolved DID as a property of the DID document. This is the purpose of the equivalentId property.

DID document metadata MAY include an equivalentId property. If present, the value MUST be a set where each item is a string that conforms to the rules in Section . The relationship is a statement that each equivalentId value is logically equivalent to the id property value and thus refers to the same DID subject. Each equivalentId DID value MUST be produced by, and a form of, the same DID method as the id property value. (e.g., did:example:abc == did:example:ABC)

A conforming DID method specification MUST guarantee that each equivalentId value is logically equivalent to the id property value.

A requesting party is expected to retain the values from the id and equivalentId properties to ensure any subsequent interactions with any of the values they contain are correctly handled as logically equivalent (e.g., retain all variants in a database so an interaction with any one maps to the same underlying account).

Note: Stronger equivalence

equivalentId is a much stronger form of equivalence than alsoKnownAs because the equivalence MUST be guaranteed by the governing DID method. equivalentId represents a full graph merge because the same DID document describes both the equivalentId DID and the id property DID.

If a requesting party does not retain the values from the id and equivalentId properties and ensure any subsequent interactions with any of the values they contain are correctly handled as logically equivalent, there might be negative or unexpected issues that arise. Implementers are strongly advised to observe the directives related to this metadata property.

canonicalId

The canonicalId property is identical to the equivalentId property except: a) it is associated with a single value rather than a set, and b) the DID is defined to be the canonical ID for the DID subject within the scope of the containing DID document.

DID document metadata MAY include a canonicalId property. If present, the value MUST be a string that conforms to the rules in Section . The relationship is a statement that the canonicalId value is logically equivalent to the id property value and that the canonicalId value is defined by the DID method to be the canonical ID for the DID subject in the scope of the containing DID document. A canonicalId value MUST be produced by, and a form of, the same DID method as the id property value. (e.g., did:example:abc == did:example:ABC).

A conforming DID method specification MUST guarantee that the canonicalId value is logically equivalent to the id property value.

A requesting party is expected to use the canonicalId value as its primary ID value for the DID subject and treat all other equivalent values as secondary aliases (e.g., update corresponding primary references in their systems to reflect the new canonical ID directive).

Note: Canonical equivalence

canonicalId is the same statement of equivalence as equivalentId except it is constrained to a single value that is defined to be canonical for the DID subject in the scope of the DID document. Like equivalentId, canonicalId represents a full graph merge because the same DID document describes both the canonicalId DID and the id property DID.

If a resolving party does not use the canonicalId value as its primary ID value for the DID subject and treat all other equivalent values as secondary aliases, there might be negative or unexpected issues that arise related to user experience. Implementers are strongly advised to observe the directives related to this metadata property.

3.4 Algorithm

The following DID resolution algorithm MUST be implemented by a conformant DID resolver.

  1. Validate that the input DID conforms to the did rule of the DID Syntax. If not, the DID resolver MUST return the following result:
    1. didResolutionMetadata: «[ "error" → "invalidDid" ]»
    2. didDocument: null
    3. didDocumentMetadata: «[ ]»
  2. Determine whether the DID method of the input DID is supported by the DID resolver that implements this algorithm. If not, the DID resolver MUST return the following result:
    1. didResolutionMetadata: «[ "error" → "methodNotSupported" ]»
    2. didDocument: null
    3. didDocumentMetadata: «[ ]»
  3. Obtain the DID document for the input DID by executing the Read operation against the input DID's verifiable data registry, as defined by the input DID method:
    1. Besides the input DID, all additional resolution options of this algorithm MUST be passed to the Read operation of the input DID method.
    2. If the input DID does not exist, return the following result:
      1. didResolutionMetadata: «[ "error" → "notFound" ]»
      2. didDocument: null
      3. didDocumentMetadata: «[ ]»
    3. If the input DID has been deactivated, return the following result:
      1. didResolutionMetadata: «[ ]»
      2. didDocument: null
      3. didDocumentMetadata: «[ "deactivated" → true ]»
    4. The result of the Read operation is called the output DID document.
  4. Validate that the output DID document conforms to a conformant representation of the DID document data model. If not, the DID resolver MUST raise an error.
Issue 5: Discuss how to treat deactivated DIDs enhancementdiscuss

There is discussion how a DID that has been deactivated should be treated during the DID resolution process.

Issue 13: Validate signatures/proofs of DID Document

Specify how signatures/proofs on a DID document should be verified during the DID resolution process.

Issue

Should we define functionality that enables discovery of the list of DID methods or other capabilities that are supported by a DID resolver? Or is this implementation-specific and out-of-scope for this spec? For example, see here and here.

4. DID URL Dereferencing

The DID URL dereferencing function dereferences a DID URL into a resource with contents depending on the DID URL's components, including the DID method, method-specific identifier, path, query, and fragment. This process depends on DID resolution of the DID contained in the DID URL. DID URL dereferencing might involve multiple steps (e.g., when the DID URL being dereferenced includes a fragment), and the function is defined to return the final resource after all steps are completed. The following figure depicts the relationship described above.


DIDs resolve to DID documents; DID URLs contains a DID; DID URLs dereferenced to DID document fragments or
external resources.
Figure 2 Overview of DID URL dereference See also: narrative description.

The top left part of the diagram contains a rectangle with black outline, labeled "DID".

The bottom left part of the diagram contains a rectangle with black outline, labeled "DID URL". This rectangle contains four smaller black-outlined rectangles, aligned in a horizontal row adjacent to each other. These smaller rectangles are labeled, in order, "DID", "path", "query", and "fragment.

The top right part of the diagram contains a rectangle with black outline, labeled "DID document". This rectangle contains three smaller black-outlined rectangles. These smaller rectangles are labeled "id", "(property X)", and "(property Y)", and are surrounded by multiple series of three dots (ellipses). A curved black arrow, labeled "DID document - relative fragment dereference", extends from the rectangle labeled "(property X)", and points to the rectangle labeled "(property Y)".

The bottom right part of the diagram contains an oval shape with black outline, labeled "Resource".

A black arrow, labeled "resolves to a DID document", extends from the rectangle in the top left part of the diagram, labeled "DID", and points to the rectangle in the top right part of diagram, labeled "DID document".

A black arrow, labeled "refers to", extends from the rectangle in the top right part of the diagram, labeled "DID document", and points to the oval shape in the bottom right part of diagram, labeled "Resource".

A black arrow, labeled "contains", extends from the small rectangle labeled "DID" inside the rectangle in the bottom left part of the diagram, labeled "DID URL", and points to the rectangle in the top left part of diagram, labeled "DID".

A black arrow, labeled "dereferences to a DID document", extends from the rectangle in the bottom left part of the diagram, labeled "DID URL", and points to the rectangle in the top right part of diagram, labeled "DID document".

A black arrow, labeled "dereferences to a resource", extends from the rectangle in the bottom left part of the diagram, labeled "DID URL", and points to the oval shape in the bottom right part of diagram, labeled "Resource".

All conforming DID resolvers implement the following function which has the following abstract form:

dereference(didUrl, dereferenceOptions) →
   « dereferencingMetadata, contentStream, contentMetadata »

The input variables of the dereference function are as follows:

didUrl
A conformant DID URL as a single string. This is the DID URL to dereference. To dereference a DID fragment, the complete DID URL including the DID fragment MUST be used. This input is REQUIRED.
Note: DID URL dereferencer patterns

While it is valid for any didUrl to be passed to a DID URL dereferencer, implementers are expected to refer to 4. DID URL Dereferencing to further understand common patterns for how a DID URL is expected to be dereferenced.

dereferencingOptions
A metadata structure consisting of input options to the dereference function in addition to the didUrl itself. Properties defined by this specification are in 4.1 DID URL Dereferencing Options. This input is REQUIRED, but the structure MAY be empty.

This function returns multiple values, and no limitations are placed on how these values are returned together. The return values of the dereference include dereferencingMetadata, contentStream, and contentMetadata:

dereferencingMetadata
A metadata structure consisting of values relating to the results of the DID URL dereferencing process. This structure is REQUIRED, and in the case of an error in the dereferencing process, this MUST NOT be empty. Properties defined by this specification are in 4.2 DID URL Dereferencing Metadata. If the dereferencing is not successful, this structure MUST contain an error property describing the error.
contentStream
If the dereferencing function was called and successful, this MUST contain a resource corresponding to the DID URL. The contentStream MAY be a resource such as a DID document that is serializable in one of the conformant representations, a verification method, a service, or any other resource format that can be identified via a Media Type and obtained through the resolution process. If the dereferencing is unsuccessful, this value MUST be empty.
contentMetadata
If the dereferencing is successful, this MUST be a metadata structure, but the structure MAY be empty. This structure contains metadata about the contentStream. If the contentStream is a DID document, this MUST be a didDocumentMetadata structure as described in DID Resolution. If the dereferencing is unsuccessful, this output MUST be an empty metadata structure.

Conforming DID URL dereferencing implementations do not alter the signature of these functions in any way. DID URL dereferencing implementations might map the dereference function to a method-specific internal function to perform the actual DID URL dereferencing process. DID URL dereferencing implementations might implement and expose additional functions with different signatures in addition to the dereference function specified here.

4.1 DID URL Dereferencing Options

The possible properties within this structure and their possible values SHOULD be registered in the DID Specification Registries [DID-SPEC-REGISTRIES]. This specification defines the following common properties for dereferencing options:

accept
The Media Type that the caller prefers for contentStream. The Media Type MUST be expressed as an ASCII string. The DID URL dereferencing implementation SHOULD use this value to determine the contentType of the representation contained in the returned value if such a representation is supported and available.

4.2 DID URL Dereferencing Metadata

The possible properties within this structure and their possible values are registered in the DID Specification Registries [DID-SPEC-REGISTRIES]. This specification defines the following common properties.

contentType
The Media Type of the returned contentStream SHOULD be expressed using this property if dereferencing is successful. The Media Type value MUST be expressed as an ASCII string.
error
The error code from the dereferencing process. This property is REQUIRED when there is an error in the dereferencing process. The value of this property MUST be a single keyword expressed as an ASCII string. The possible property values of this field SHOULD be registered in the DID Specification Registries [DID-SPEC-REGISTRIES]. This specification defines the following common error values:
invalidDidUrl
The DID URL supplied to the DID URL dereferencing function does not conform to valid syntax. (See .)
notFound
The DID URL dereferencer was unable to find the contentStream resulting from this dereferencing request.

4.3 Algorithm

The following DID URL dereferencing algorithm MUST be implemented by a conformant DID resolver. In accordance with [RFC3986], it consists of the following steps: Resolving the DID, dereferencing the primary resource, and dereferencing the secondary resource (only if the input DID URL contains a DID fragment:

  1. Validate that the input DID URL conforms to the did-url rule of the DID URL Syntax. If not, the DID URL dereferencer MUST return the following result:
    1. dereferencingMetadata: «[ "error" → "invalidDidUrl" ]»
    2. contentStream: null
    3. contentMetadata: «[ ]»
  2. Obtain the DID document for the input DID by executing the DID resolution algorithm as defined in 3. DID Resolution. All DID parameters of the input DID URL MUST be passed as resolution options to the DID Resolution algorithm. If the input DID does not exist, return a null result. Otherwise, the result is called the resolved DID document.
  3. If present, separate the DID fragment from the input DID URL. Execute the algorithm for 4.3.1 Dereferencing the Primary Resource, with the input DID URL adjusted accordingly.
  4. If the original input DID URL contained a DID fragment, execute the algorithm for 4.3.2 Dereferencing the Secondary Resource.

4.3.1 Dereferencing the Primary Resource

  1. If the input DID URL contains the DID parameter service and optionally the relativeRef DID parameter:
    did:example:1234?service=files&relativeRef=%2Fmyresume%2Fdoc%3Fversion%3Dlatest
    1. From the resolved DID document, select the service endpoint whose id property contains a fragment which matches the value of the service DID parameter of the input DID URL. This is called the input service endpoint.
    2. Execute the Service Endpoint Construction algorithm:
      1. Read the value of the serviceEndpoint property of the input service endpoint. This is called the input service endpoint URL.
      2. Pass the input DID URL and input service endpoint URL to the Service Endpoint Construction algorithm.
      3. The result is called the output service endpoint URL.
    3. Return the output service endpoint URL.
  2. Otherwise, if the input DID URL contains no DID path and no DID query:
    did:example:1234
    1. Return the resolved DID document.
  3. Otherwise, if the input DID URL contains a DID path and/or DID query:
    did:example:1234/custom/path?customquery
    1. The applicable DID method MAY specify how to dereference the input DID URL.
    2. The client MAY be able to dereference the input DID URL in an application-specific way.
  4. If neither this algorithm, nor the applicable DID method, nor the client is able to dereference the input DID URL, return the following result:
    1. dereferencingMetadata: «[ "error" → "notFound" ]»
    2. contentStream: null
    3. contentMetadata: «[ ]»
Issue 85: Request service by type enhancement

There have been discussions whether in addition to the DID parameter service, there could also be a DID parameter serviceType to select services based on their type rather than ID. See comments by Dave Longley about serviceType.

4.3.2 Dereferencing the Secondary Resource

If the input DID URL contains a DID fragment, then dereferencing of the secondary resource identified by the URL is dependent not on the URI scheme, but on the media type ([RFC2046]) of the primary resource, i.e., on the result of 4.3.1 Dereferencing the Primary Resource.

  1. If the result of 4.3.1 Dereferencing the Primary Resource is a resolved DID document with media type application/did+ld+json, and the input DID URL contains a DID fragment:
    did:example:1234#keys-1
    1. From the resolved DID document, select the JSON-LD object whose id property matches the input DID URL, e.g., a public key or service endpoint in the DID document. This is called the output resource. When selecting the JSON-LD object from the DID document, the absolute DID URL used to identify a graph node MUST be unique and present only once in the DID document. If the identifier of the graph node is not unique, including if a relative or base IRI mapped to an absolute IRI collides with a different graph node's absolute IRI, then an error MUST be thrown.
    2. Return the output resource.
      Issue 9: DID = Base IRI? pending-close

      Mention relative IRIs and that the DID itself is considered the base IRI for the JSON-LD parser. Mention potential attack vector if @base is injected into the DID document.

      Also see this discussion on fully qualified DID URLs as the value of the id field.

  2. Otherwise, if the result of 4.3.1 Dereferencing the Primary Resource is an output service endpoint URL, and the input DID URL contains a DID fragment:
    did:example:1234?service=files&relativeRef=%2Fmyresume%2Fdoc%3Fversion%3Dlatest#intro
    1. If the output service endpoint URL contains a fragment component, raise an error.
    2. Append the DID fragment to the output service endpoint URL. In other words, the output service endpoint URL "inherits" the DID fragment of the input DID URL.
    3. Return the output service endpoint URL.
  3. Otherwise, dereference the secondary resource as defined by the media type ([RFC2046]) of the primary resource.
Note

This behavior of the DID fragment is analogous to the handling of a fragment in an HTTP URL in the case when dereferencing it returns an HTTP 3xx (Redirection) response with a Location header (see section 7.1.2 of [RFC7231].

Note

This use of the DID fragment is consistent with the definition of the fragment identifier in [RFC3986]. It identifies a secondary resource which is a subset of the primary resource (the DID document).

Note

This use of the DID fragment is furthermore consistent with the concept of Hash URIs for the Semantic Web [COOL-URIS].

Issue

Perhaps we can find a good reference somewhere from RDF, JSON-LD or Solid specifications that defines clearly the ability to use the fragment for identifying a specific resource in an RDF document.

4.4 Examples

Given the following input DID URL:

did:example:123456789abcdefghi#keys-1

... and the following resolved DID document:

{
	"@context": "https://www.w3.org/ns/did/v1",
	"id": "did:example:123456789abcdefghi",
	"verificationMethod": [{
		"id": "did:example:123456789abcdefghi#keys-1",
		"type": "Ed25519VerificationKey2018",
		"controller": "did:example:123456789abcdefghi",
		"publicKeyBase58": "H3C2AVvLMv6gmMNam3uVAjZpfkcJCwDwnZn6z3wXmqPV"
	}],
	"service": [{
		"id": "did:example:123456789abcdefghi#agent",
		"type": "AgentService",
		"serviceEndpoint": "https://agent.example.com/8377464"
	}, {
		"id": "did:example:123456789abcdefghi#messages",
		"type": "MessagingService",
		"serviceEndpoint": "https://example.com/messages/8377464"
	}]
}

... then the result of the 4. DID URL Dereferencing algorithm is the following output resource:

{
	"@context": "https://www.w3.org/ns/did/v1",
	"id": "did:example:123456789abcdefghi#keys-1",
	"type": "Ed25519VerificationKey2018",
	"controller": "did:example:123456789abcdefghi",
	"publicKeyBase58": "H3C2AVvLMv6gmMNam3uVAjZpfkcJCwDwnZn6z3wXmqPV"
}

Given the following input DID URL and the same resolved DID document as above:

did:example:123456789abcdefghi?service=messages&relativeRef=%2Fsome%2Fpath%3Fquery#frag

... then the result of the 4. DID URL Dereferencing algorithm is the following output service endpoint URL:

https://example.com/messages/8377464/some/path?query#frag
Diagram showing how a DID URL can be dereferenced to a service endpoint URL
Figure 3 Dereferencing a DID URL to a service endpoint URL.
Issue

Change the diagram and/or examples to make them consistent.

5. Metadata Structure

Input and output metadata is often involved during the DID Resolution, DID URL dereferencing, and other DID-related processes. The structure used to communicate this metadata MUST be a map of properties. Each property name MUST be a string. Each property value MUST be a string, map, list, set, boolean, or null. The values within any complex data structures such as maps and lists MUST be one of these data types as well. All metadata property definitions registered in the DID Specification Registries [DID-SPEC-REGISTRIES] MUST define the value type, including any additional formats or restrictions to that value (for example, a string formatted as a date or as a decimal integer). It is RECOMMENDED that property definitions use strings for values. The entire metadata structure MUST be serializable according to the JSON serialization rules in the [INFRA] specification. Implementations MAY serialize the metadata structure to other data formats.

All implementations of functions that use metadata structures as either input or output are able to fully represent all data types described here in a deterministic fashion. As inputs and outputs using metadata structures are defined in terms of data types and not their serialization, the method for representation is internal to the implementation of the function and is out of scope of this specification.

The following example demonstrates a JSON-encoded metadata structure that might be used as DID resolution input metadata.

Example 11: JSON-encoded DID resolution input metadata example
{
"accept": "application/did+ld+json"
}

This example corresponds to a metadata structure of the following format:

Example 12: DID resolution input metadata example
«[
"accept""application/did+ld+json"

The next example demonstrates a JSON-encoded metadata structure that might be used as DID resolution metadata if a DID was not found.

Example 13: JSON-encoded DID resolution metadata example
{
"error": "notFound"
}

This example corresponds to a metadata structure of the following format:

Example 14: DID resolution metadata example
«[
"error""notFound"

The next example demonstrates a JSON-encoded metadata structure that might be used as DID document metadata to describe timestamps associated with the DID document.

Example 15: JSON-encoded DID document metadata example
{
"created": "2019-03-23T06:35:22Z",
"updated": "2023-08-10T13:40:06Z"
}

This example corresponds to a metadata structure of the following format:

Example 16: DID document metadata example
«[
"created""2019-03-23T06:35:22Z",
"updated""2023-08-10T13:40:06Z"

6. DID Resolution Architectures

Issue

TODO: Describe how DID resolvers are implemented and used, describe the relevance of DID methods. Explain the difference between "method architectures" and "resolver architectures".

6.1 Method Architectures

The DID resolution algorithm involves executing the Read operation on a DID according to its DID method (see 3. DID Resolution).

Note

The mechanics of the "Read" operation can vary considerably between DID methods. In particular, no assumption should be made that:

  • ... an immutable blockchain is used as (part of) the verifiable data registry.
  • ... interaction with a remote network is required during execution of the "Read" operation.
  • ... an actual DID document is stored in plain-text on a verifiable data registry, or that the DID document can simply be retrieved via a standard protocol such as HTTP(S). While some DID methods may define their "Read" operation this way, others may define more complex multi-step processes that involve on-the-fly construction of a "virtual" DID document.
Issue

As an example, mention what it means to "resolve" peer/off-ledger/microledger/edgechain DIDs (for instance, see [DID-PEER] and here).

Issue

As an example, mention what it means to "resolve" DIDs that are simply wrapped public keys (for instance, see [DID-KEY] and here).

Depending on the exact nature of the DID method's "Read" operation, the interaction between a DID resolver and the verifiable data registry may be implemented as a verifiable read or unverifiable read:

Diagram showing a 'verifiable read' implementation of a DID method.
Figure 4 A verifiable read implementation of a DID method.
Diagram showing an 'unverifiable read' implementation of a DID method.
Figure 5 An unverifiable read implementation of a DID method.

A verifiable read maximizes confidence in the integrity and correctness of the result of the "Read" operation ‐ to the extent possible under the applicable DID method. It can be implemented in a variety of ways, for example:

An unverifiable read does not have such guarantees and is therefore less desirable, for example:

Whether or not a verifiable read is possible depends not only on a DID method itself, but also on the way how a DID resolver implements it. DID methods MAY define multiple different ways of implementing their "Read" operation(s) and SHOULD offer guidance on how to implement a verifiable read in at least one way.

Note

The guarantees associated with a verifiable read are still always limited by the architectures, protocols, cryptography, and other aspects of the underlying verifiable data registry. The strongest forms of verifiable read implementations are considered those that do not require any interaction with a remote network at all (for example, see [DID-KEY]), or that minimize dependencies on specific network infrastructure and reduce the "root of trust" to proven entropy and cryptography alone (for example, see [KERI]).

Issue

TODO: Describe how a client can potentially verify the result of a "Read" operation independently even if it does not trust the DID resolver (e.g., using state proofs).

A DID resolver MUST support the DID resolution algorithm for at least one DID method and MAY support it for multiple DID methods:

Diagram showing a DID resolver that supports multiple DID methods.
Figure 6 A DID resolver that supports multiple DID methods.

In this case, the above considerations about verifiable read and unverifiable read implementations apply to each supported DID method individually.

6.2 Resolver Architectures

The algorithms for DID resolution and DID URL dereferencing are defined as abstract functions (see 3. DID Resolution and 4. DID URL Dereferencing).

Those algorithms are implemented by DID resolvers. A DID resolver is invoked by a client via a binding. bindings define how the abstract functions are realized using concrete programming or communication interfaces. It is possible to distinguish between local bindings (such as a local command line tool or library API) and remote bindings (such as the HTTP(S) binding).

Diagram showing a DID resolver with a 'local binding'.
Figure 7 A local binding for a DID resolver.
Diagram showing a DID resolver with a 'remote binding'.
Figure 8 A remote binding for a DID resolver.
Issue 28: 'remote' vs 'local' DID Resolvers

TODO: Describe local bindings vs. remote bindings, and implications for privacy, security and trust.

Also describe mitigations against potential downsides of remote bindings, e.g.:

Issue

TODO: Discuss DID resolution in constrained user agents such as mobile apps and browsers.

The following diagram shows how the resolve() and resolveRepresentation() functions use production and consumption rules of DID document representation can apply in an architecture that involves both a local resolver and a remote resolver.

Diagram showing a local and remote DID resolver executing the resolve() and resolveRepresentation() functions.
Figure 9 Production and consumption in an architecture that involves both a local and a remote DID resolver.

6.2.1 Proxied Resolution

A DID resolver MAY invoke another DID resolver, which serves as a proxy that executes the DID resolution algorithm as defined in 3. DID Resolution.

The first DID resolver then acts as a client and chooses a suitable binding for invoking the second DID resolver. For example, a DID resolver may be invoked via a local binding (such as a command line tool), which in turn invokes another DID resolver via a remote binding (such as the HTTP(S) binding).

Diagram showing two DID resolvers, one invoked via 'local binding', the other invoked via 'remote binding'.
Figure 10 A client invokes a DID resolver via local binding which invokes another DID resolver via remote binding, which in turn supports resolving multiple DID methods.
Note

This is similar to a "stub resolver" invoking a "recursive resolver" in DNS architecture, although the concepts are not entirely comparable (DNS Resolution uses a single concrete protocol, whereas DID resolution is an abstract function realized by different DID methods and different bindings).

6.2.2 Client-Side Dereferencing

Different parts of the DID URL dereferencing algorithm may be performed by different components of a Resolver Architecture.

Specifically, when a DID URL with a DID fragment is dereferenced, then Dereferencing the Primary Resource is done by the DID resolver, and Dereferencing the Secondary Resource is done by the client.

Example: Given the DID URL did:xyz:1234#keys-1, a DID resolver could be invoked via local binding for Dereferencing the Primary Resource (i.e., the DID document), and the client could complete the DID URL dereferencing algorithm by Dereferencing the Secondary Resource (i.e., a part of the DID document).

Diagram showing client-side dereferencing of a DID URL by a DID resolver and a client
Figure 11 Client-side dereferencing of a DID URL by a DID resolver and a client.

Example: Given the DID URL did:xyz:1234#keys-1, a DID resolver could be invoked via local binding which invokes another DID resolver via remote binding for Dereferencing the Primary Resource (i.e., the DID document), and the client could complete the DID URL dereferencing algorithm by Dereferencing the Secondary Resource (i.e., a part of the DID document).

Diagram showing client-side dereferencing of a DID URL by two DID resolvers and a client
Figure 12 Client-side dereferencing (in combination with Proxied Resolution) of a DID URL by two DID resolvers and a client.

Example: Given the DID URL did:xyz:1234?service=agent&relativeRef=%2Fsome%2Fpath%3Fquery#frag, a DID resolver could be invoked for Dereferencing the Primary Resource (i.e., a service endpoint URL), and the client could complete the DID URL dereferencing algorithm by Dereferencing the Secondary Resource (i.e., a service endpoint URL with a fragment).

Diagram showing client-side dereferencing of a DID URL by a DID resolver and a client
Figure 13 Client-side dereferencing of a DID URL by a DID resolver and a client.

7. DID Resolution Result

This section defines a data structure that represents the result of the algorithm described in 3. DID Resolution. A DID resolution result contains a DID document as well as DID resolution metadata and DID document metadata.

The media type of this data structure is defined to be application/ld+json;profile="https://w3id.org/did-resolution".

7.1 Example

Example 17: Example DID resolution result
{
	"@context": "https://w3id.org/did-resolution/v1",
	"didDocument": {
		"@context": "https://www.w3.org/ns/did/v1",
		"id": "did:example:123456789abcdefghi",
		"authentication": [{
			"id": "did:example:123456789abcdefghi#keys-1",
			"type": "Ed25519VerificationKey2018",
			"controller": "did:example:123456789abcdefghi",
			"publicKeyBase58": "H3C2AVvLMv6gmMNam3uVAjZpfkcJCwDwnZn6z3wXmqPV"
		}],
		"service": [{
			"id":"did:example:123456789abcdefghi#vcs",
			"type": "VerifiableCredentialService",
			"serviceEndpoint": "https://example.com/vc/"
		}]
	},
	"didResolutionMetadata": {
		"contentType": "application/did+ld+json",
		"retrieved": "2024-06-01T19:73:24Z",
	},
	"didDocumentMetadata": {
		"created": "2019-03-23T06:35:22Z",
		"updated": "2023-08-10T13:40:06Z",
		"method": {
			"nymResponse": {
				"result": {
					"data": "{\"dest\":\"WRfXPg8dantKVubE3HX8pw\",\"identifier\":\"V4SGRU86Z58d6TV7PBUe6f\",\"role\":\"0\",\"seqNo\":11,\"txnTime\":1524055264,\"verkey\":\"H3C2AVvLMv6gmMNam3uVAjZpfkcJCwDwnZn6z3wXmqPV\"}",
					"type": "105",
					"txnTime": 1.524055264E9,
					"seqNo": 11.0,
					"reqId": 1.52725687080231475E18,
					"identifier": "HixkhyA4dXGz9yxmLQC4PU",
					"dest": "WRfXPg8dantKVubE3HX8pw"
				},
				"op": "REPLY"
			},
			"attrResponse": {
				"result": {
					"identifier": "HixkhyA4dXGz9yxmLQC4PU",
					"seqNo": 12.0,
					"raw": "endpoint",
					"dest": "WRfXPg8dantKVubE3HX8pw",
					"data": "{\"endpoint\":{\"xdi\":\"http://127.0.0.1:8080/xdi\"}}",
					"txnTime": 1.524055265E9,
					"type": "104",
					"reqId": 1.52725687092557056E18
				},
				"op": "REPLY"
			}
		}
	}
}
Issue 23: The did is not a url for the did, but for a resolution structure which as yet has no name pending-close

See corresponding open issue.

Issue

Need to define how this data structure works exactly, and whether it always contains a DID document or can also contain other results.

7.2 DID Document

A DID document associated with a DID. The result of 3. DID Resolution.

7.3 DID Resolution Metadata

This is a metadata structure (see section Metadata Structure in [DID-CORE]) that contains metadata about the DID Resolution process.

This metadata typically changes between invocations of the DID Resolution functions as it represents data about the resolution process itself.

The source of this metadata is the DID resolver.

Examples of DID Resolution Metadata include:

See also section DID Resolution Metadata in [DID-CORE].

7.4 DID Document Metadata

This is a metadata structure (see section Metadata Structure in [DID-CORE]) that contains metadata about a DID Document.

This metadata typically does not change between invocations of the DID Resolution function unless the DID document changes, as it represents data about the DID document.

The sources of this metadata are the DID controller and/or the DID method.

Examples of DID Document Metadata include:

DID Document Metadata may also include method-specific metadata, e.g.:

See also section DID Document Metadata in [DID-CORE].

Issue

For certain data, it may be debatable whether it should be part of the DID document (i.e., data that describes the DID Subject), or whether it is metadata (i.e., data about the DID document or about the DID resolution process). For example the URL of the "Continuation DID document" in the BTCR method.

8. DID URL Dereferencing Result

This section defines a data structure that represents the result of the algorithm described in 4. DID URL Dereferencing. A DID URL dereferencing result contains arbitrary content as well as DID resolution metadata and content metadata.

Issue 69: DID Resolution Result for DID URL Dereferencing enhancement

See corresponding open issue.

The media type of this data structure is defined to be application/ld+json;profile="https://w3id.org/did-resolution".

8.1 Example

Example 18: Example DID URL dereferencing result
{
	"@context": "https://w3id.org/did-resolution/v1",
	"content": {
		"@context": "https://www.w3.org/ns/did/v1",
		"id": "did:example:123456789abcdefghi",
		"authentication": [{
			"id": "did:example:123456789abcdefghi#keys-1",
			"type": "Ed25519VerificationKey2018",
			"controller": "did:example:123456789abcdefghi",
			"publicKeyBase58": "H3C2AVvLMv6gmMNam3uVAjZpfkcJCwDwnZn6z3wXmqPV"
		}],
		"service": [{
			"id":"did:example:123456789abcdefghi#vcs",
			"type": "VerifiableCredentialService",
			"serviceEndpoint": "https://example.com/vc/"
		}]
	},
	"didUrlDereferencingMetadata": {
		"contentType": "application/did+ld+json",
		"retrieved": "2024-06-01T19:73:24Z",
	},
	"contentMetadata": {
		"created": "2019-03-23T06:35:22Z",
		"updated": "2023-08-10T13:40:06Z",
		"method": {
			"nymResponse": {
				"result": {
					"data": "{\"dest\":\"WRfXPg8dantKVubE3HX8pw\",\"identifier\":\"V4SGRU86Z58d6TV7PBUe6f\",\"role\":\"0\",\"seqNo\":11,\"txnTime\":1524055264,\"verkey\":\"H3C2AVvLMv6gmMNam3uVAjZpfkcJCwDwnZn6z3wXmqPV\"}",
					"type": "105",
					"txnTime": 1.524055264E9,
					"seqNo": 11.0,
					"reqId": 1.52725687080231475E18,
					"identifier": "HixkhyA4dXGz9yxmLQC4PU",
					"dest": "WRfXPg8dantKVubE3HX8pw"
				},
				"op": "REPLY"
			},
			"attrResponse": {
				"result": {
					"identifier": "HixkhyA4dXGz9yxmLQC4PU",
					"seqNo": 12.0,
					"raw": "endpoint",
					"dest": "WRfXPg8dantKVubE3HX8pw",
					"data": "{\"endpoint\":{\"xdi\":\"http://127.0.0.1:8080/xdi\"}}",
					"txnTime": 1.524055265E9,
					"type": "104",
					"reqId": 1.52725687092557056E18
				},
				"op": "REPLY"
			}
		}
	}
}

8.2 Content

Arbitrary content associated with a DID URL. The result of 4. DID URL Dereferencing.

8.3 DID URL Dereferencing Metadata

This is a metadata structure (see section Metadata Structure in [DID-CORE]) that contains metadata about the DID URL Dereferencing process.

This metadata typically changes between invocations of the DID URL Dereferencing functions as it represents data about the dereferencing process itself.

Issue

Add more details how DID URL dereferencing metadata works.

See also section DID URL Dereferencing Metadata in [DID-CORE].

8.4 Content Metadata

This is a metadata structure (see section Metadata Structure in [DID-CORE]) that contains metadata about the content.

This metadata typically does not change between invocations of the DID URL Dereferencing function unless the content changes, as it represents data about the content.

Issue

Add more details how content metadata works.

9. Errors

9.1 invalidDid

If an invalid DID is detected during DID Resolution, the value of the DID Resolution Metadata error property MUST be invalidDid as defined in section DID Resolution Metadata in [DID-CORE].

9.2 invalidDidUrl

If an invalid DID URL is detected during DID Resolution or DID URL dereferencing, the value of the DID Resolution or DID URL Dereferencing Metadata error property MUST be invalidDidUrl as defined in section DID URL Dereferencing Metadata in [DID-CORE].

9.3 notFound

If during DID Resolution or DID URL dereferencing a DID or DID URL doesn't exist, the value of the DID Resolution or DID URL dereferencing Metadata error property MUST be notFound as defined in sections DID Resolution Metadata and DID URL Dereferencing Metadata in [DID-CORE].

9.4 representationNotSupported

If a DID document representation is not supported during DID Resolution or DID URL dereferencing, the value of the DID Resolution Metadata error property MUST be representationNotSupported as defined in section DID Resolution Metadata in [DID-CORE].

9.5 methodNotSupported

If a DID method is not supported during DID Resolution or DID URL dereferencing, the value of the DID Resolution or DID URL Dereferencing Metadata error property MUST be methodNotSupported.

9.6 internalError

When an unexpected error occurs during DID Resolution or DID URL dereferencing, the value of the DID Resolution or DID URL Dereferencing Metadata error property MUST be internalError.

9.7 invalidPublicKey

If an invalid public key value is detected during DID Resolution or DID URL dereferencing, the value of the DID Resolution or DID URL Dereferencing Metadata error property MUST be invalidPublicKey.

9.8 invalidPublicKeyLength

If the byte length of rawPublicKeyBytes does not match the expected public key length for the associated multicodecValue during DID Resolution or DID URL dereferencing, the value of the DID Resolution or DID URL Dereferencing Metadata error property MUST be invalidPublicKeyLength.

9.9 invalidPublicKeyType

If an invalid public key type is detected during DID Resolution or DID URL dereferencing, the value of the DID Resolution or DID URL Dereferencing Metadata error property MUST be invalidPublicKeyType.

9.10 unsupportedPublicKeyType

If an unsupported public key type is detected during DID Resolution or DID URL dereferencing, the value of the DID Resolution or DID URL Dereferencing Metadata error property MUST be unsupportedPublicKeyType.

10. Bindings

This section defines bindings for the abstract algorithms in sections 3. DID Resolution and 4. DID URL Dereferencing.

10.1 HTTP(S) Binding

This section defines a DID resolver binding which exposes the DID resolution and/or DID URL dereferencing functions (including all resolution options and output data) via an HTTP(S) endpoint. See 6.2 Resolver Architectures.

The HTTP(S) binding for DID resolvers requires a known HTTP(S) URL called the DID resolver HTTP(S) endpoint.

Using this binding, the DID resolution function (see 3. DID Resolution) and/or DID URL dereferencing function (see 4. DID URL Dereferencing) can be executed as follows:

  1. Initialize a request HTTP(S) URL with the DID resolver HTTP(S) endpoint.
    1. Append the input DID or input DID URL to the request HTTP(S) URL. Certain characters MUST be percent-encoded (as specified in RFC3986 Section 2.1).
    2. Encode the accept resolution option as the Accept HTTP header in the request.
    3. Encode all other resolution options as query parameters in the request HTTP(S) URL.
  2. Execute an HTTP GET request on the request HTTP(S) URL.
  3. Dereference the input DID or input DID URL by executing the DID URL dereferencing algorithm as defined in 4. DID URL Dereferencing
  4. If the output of the DID URL dereferencing function contains the dereferencingMetadata property error, then the HTTP response status code MUST be set to the value that corresponds to the value of the error property, according to the following table:
    error HTTP status code
    invalidDid 400
    invalidDidUrl 400
    notFound 404
    representationNotSupported 406
    methodNotSupported 501
    internalError 500
    (any other value) 500
  5. If the output of the DID URL dereferencing function contains the didDocumentMetadata property deactivated with value true:
    1. The HTTP response status code MUST be 410.
  6. If the output of the DID URL dereferencing function contains the didDocumentStream:
    1. If the value of the Accept HTTP header is absent or application/did+ld+json (or other media type of a conformant representation of a DID document):
      1. The HTTP response status code MUST be 200.
      2. The HTTP response MUST contain a Content-Type header. The value of this header MUST be application/did+ld+json (or other media type of a conformant representation of a DID document).
      3. The HTTP response body MUST contain the didDocumentStream, in the representation corresponding to the Accept HTTP header.
    2. If the value of the Accept HTTP header is application/ld+json;profile="https://w3id.org/did-resolution":
      1. Produce a DID resolution result (see (see 7. DID Resolution Result) and populate it with the didDocumentStream, didResolutionMetadata, and didDocumentMetadata that are the output of the DID resolution function.
      2. The HTTP response status code MUST be 200.
      3. The HTTP response MUST contain a Content-Type header. The value of this header MUST be application/ld+json;profile="https://w3id.org/did-resolution".
      4. The HTTP response body MUST contain the produced DID resolution result.
  7. If the output of the DID URL dereferencing function is a service endpoint URL:
    1. The HTTP response status code MUST be 303.
    2. The HTTP response MUST contain an Location header. The value of this header MUST be the output service endpoint URL.

See here for an OpenAPI definition.

Issue

TODO: Review HTTP(S) binding for DID resolution and DID URL dereferencing, including the following topics:

  • How are resolution options passed via HTTP(S)? Using the query string and/or HTTP headers?
  • How is the output data (DID document, DID resolution result) returned via HTTP(S)?
  • How should Accept and Content-Type HTTP headers be used? How are the resolve() and resolveRepresentation() functions called? See this issue for a discussion.
  • Are two separate HTTP(S) endpoints required/allowed for the resolve() and dereference() functions, or can/must a single HTTP(S) endpoint be used?

10.2 DID Resolution Examples

Given the following DID resolver HTTP(S) endpoint:

https://dev.uniresolver.io/1.0/identifiers/

And given the following input DID:

did:sov:WRfXPg8dantKVubE3HX8pw

Then the request HTTP(S) URL is:

https://dev.uniresolver.io/1.0/identifiers/did:sov:WRfXPg8dantKVubE3HX8pw

The HTTP(S) binding can be invoked as follows:

Example 19: Example curl call to a DID resolver via HTTP(S) binding
curl -X GET https://dev.uniresolver.io/1.0/identifiers/did:sov:WRfXPg8dantKVubE3HX8pw

Additional examples of the HTTP(S) binding:

Diagram showing the invocation of resolveRepresentation() over HTTPS
Figure 14 Invocation of resolveRepresentation() over HTTP(S).
Diagram showing the invocation of resolveRepresentation() over HTTPS
Figure 15 Invocation of resolveRepresentation() over HTTP(S).

10.3 DID URL Dereferencing Examples

Additional examples of the HTTP(S) binding:

Diagram showing the invocation of dereference() over HTTPS
Figure 16 Invocation of dereference() over HTTP(S).
Diagram showing the invocation of dereference() over HTTPS
Figure 17 Invocation of dereference() over HTTP(S).

11. Service Endpoint Construction

This section defines the inputs and the algorithm of Service Endpoint Construction, which returns a service endpoint URL as output. This algorithm is used when service endpoints are selected during DID URL dereferencing (see 4. DID URL Dereferencing).

In this section, path, query, and fragment are understood as defined in [RFC3986].

11.1 Input

The inputs of the Service Endpoint Construction algorithm are an input DID URL and an input service endpoint URL.

The requirements for the inputs of the Service Endpoint Construction algorithm are as follows:

11.2 Algorithm

  1. Initialize a string output service endpoint URL to the value of the input service endpoint URL
  2. If the output service endpoint URL has a query component, remove it.
  3. If the output service endpoint URL has a fragment component, remove it.
  4. Append the path component of the input DID URL to the output service endpoint URL.
  5. If the input service endpoint URL has a query component, append ? plus the query to the output service endpoint URL.
  6. If the input DID URL has a query component, append ? plus the query to the output service endpoint URL.
  7. If the input service endpoint URL has a fragment component, append # plus the fragment to the output service endpoint URL.
  8. If the input DID URL has a fragment component, append # plus the fragment to the output service endpoint URL.
  9. Return the output service endpoint URL.
Issue

We could potentially allow query components on both the input DID URL and input service endpoint URL, if they both contain lists of key/value parameters that can be merged.

Issue

Details of the Service Endpoint Construction algorithm have been discussed in April 2019 on the CCG mailing list, e.g., here or here.

Issue

Instead of defining our own algorithm, we could potentially re-use the "Relative Resolution" algorithm defined in [RFC3986].

11.3 Example

Given the following input service endpoint URL:

https://example.com/messages/8377464

And given the following input DID URL:

did:example:123456789abcdefghi?service=messages&relativeRef=%2Fsome%2Fpath%3Fquery#frag

Then the output service endpoint URL is:

https://example.com/messages/8377464/some/path?query#frag

12. Security and Privacy Considerations

12.1 Authentication/Authorization

DID resolution and DID URL dereferencing do not involve any authentication or authorization functionality. Similar to DNS resolution, anybody can perform the process, without requiring any credentials or non-public knowledge.

Issue 38: Restricted access/Authentication/Authorization enhancement

The spec should clarify whether or not conformant resolvers MUST be public or MAY restrict access via some authentication and authorization scheme.

The current language doesn't make it clear if authentication is just out of scope or if it is disallowed.

Issue

Explain that DIDs are not necessarily globally resolvable, such as pairwise or N-wise "peer" DIDs.

See [RFC3339]: URIs have a global scope and are interpreted consistently regardless of context, though the result of that interpretation may be in relation to the end-user's context.

An advanced idea is that the result of DID resolution could be contextual or depend on policies, see this comment.

Issue

A related topic is whether (parts of) DID document could be encrypted, e.g., w3c/did-core/issues/25. Also see the use of the fragment in the IPID DID method.

12.2 Caching

A DID resolver may maintain a generic cache of DID documents. It may also maintain caches specific to certain DID methods.

The noCache resolution option can be used to request a certain kind of caching behavior.

This resolution option is OPTIONAL.

Possible values of this property are:

Caching behavior can be controlled by configuration of the DID resolver, by the noCache resolution option, or by contents of the DID document (e.g., a cacheMaxTtl field), or by a combination of these properties.

Issue 10: need TTL construct? enhancement

See corresponding open issue.

Issue

Perhaps we can re-use caching mechanisms of other protocols such as HTTP.

12.3 Versioning

If a versionId or versionTime DID parameter is provided, the DID resolution algorithm returns a specific version of the DID document.

The DID parameters versionId and versionTime are mutually exclusive.

The use of the versionId DID parameter is specific to the DID method. Its possible values may include sequential numbers, random UUIDs, content hashes, etc..

DID document metadata MAY contain a versionId property that changes with each Update operation that is performed on a DID document.

Note

While most DID methods support the Update operation, there is no requirement for DID methods to keep all previous DID document versions, therefore not all DID methods support versioning.

Issue 12: Design versioning features

See corresponding open issue.

12.4 Non-DID Identifiers

Issue 8: Discover DIDs from other identifiers discuss

There is discussion on the relationship between DID resolution and resolution of non-DID identifiers such as domain names, HTTP URIs, or e-mail addresses. This includes the questions how DIDs can be discovered from non-DID identifiers, and how links between identifiers can be verifiable.

12.5 DID Method Governance

Issue 6: DID method governance

Describe which methods a DID resolver should support, and potential implications.

13. Future Work

Note

This section lists additional DID URL dereferencing features that are under discussion and have not yet been incorporated into the algorithm.

13.1 Redirect

A service endpoint may have a serviceEndpoint property with a value that is itself a DID. This is interpreted as a "DID redirect" from the input DID to another. In this case, a "child" DID resolution process can be launched to get to a "final" service endpoint.

The follow-redirect resolution option can be supplied by a client as a hint to instruct whether redirects should be followed. This resolution option is OPTIONAL.

Issue 7: Support DIDs as serviceEndpoint? enhancement

See corresponding open issue.

Issue 36: Portable DID resolution

DID redirects could not only apply to a single service endpoint, but to an entire DID document, therefore enabling portability use cases.

{
   "id": "did:example:123456789abcdefghi#hub1",
   "type": "HubService",
   "serviceEndpoint": "did:example:xyz"
}

13.2 Proxy

A DID document may contain a "proxy" service type which would provide a mapping that needs to be followed in order to resolve to a final service URL.

Issue 35: Support "proxy" service type? enhancementpending-close

Keeping track of a proposal here w3c-ccg/did-spec#90 (comment) that a DID Document could contain a "proxy" service type which would provide a mapping that needs to be followed in order to resolve to a final service URL.

{
   "id": "did:example:123456789abcdefghi",
   "type": "ProxyService",
   "serviceEndpoint": "https://mydomain.com/proxy"
}

13.3 JSON Pointer

Issue

Several ways of selecting parts of a DID document are being discussed, including the use of JSON pointer.

See corresponding PRs here and here.

A. DID Resolution Resources

  1. DID resolvers in DID Core specification
  2. Universal Resolver
  3. did-client
  4. uPort DID resolver

B. References

B.1 Normative references

[DID-CORE]
Decentralized Identifiers (DIDs) v1.0. Manu Sporny; Amy Guy; Markus Sabadello; Drummond Reed. W3C. 19 July 2022. W3C Recommendation. URL: https://www.w3.org/TR/did-core/
[INFRA]
Infra Standard. Anne van Kesteren; Domenic Denicola. WHATWG. Living Standard. URL: https://infra.spec.whatwg.org/
[RFC2046]
Multipurpose Internet Mail Extensions (MIME) Part Two: Media Types. N. Freed; N. Borenstein. IETF. November 1996. Draft Standard. URL: https://www.rfc-editor.org/rfc/rfc2046
[RFC2119]
Key words for use in RFCs to Indicate Requirement Levels. S. Bradner. IETF. March 1997. Best Current Practice. URL: https://www.rfc-editor.org/rfc/rfc2119
[RFC3986]
Uniform Resource Identifier (URI): Generic Syntax. T. Berners-Lee; R. Fielding; L. Masinter. IETF. January 2005. Internet Standard. URL: https://www.rfc-editor.org/rfc/rfc3986
[RFC7231]
Hypertext Transfer Protocol (HTTP/1.1): Semantics and Content. R. Fielding, Ed.; J. Reschke, Ed.. IETF. June 2014. Proposed Standard. URL: https://httpwg.org/specs/rfc7231.html
[RFC8174]
Ambiguity of Uppercase vs Lowercase in RFC 2119 Key Words. B. Leiba. IETF. May 2017. Best Current Practice. URL: https://www.rfc-editor.org/rfc/rfc8174
[VC-DATA-MODEL]
Verifiable Credentials Data Model v1.1. Manu Sporny; Grant Noble; Dave Longley; Daniel Burnett; Brent Zundel; Kyle Den Hartog. W3C. 3 March 2022. W3C Recommendation. URL: https://www.w3.org/TR/vc-data-model/
[XMLSCHEMA11-2]
W3C XML Schema Definition Language (XSD) 1.1 Part 2: Datatypes. David Peterson; Sandy Gao; Ashok Malhotra; Michael Sperberg-McQueen; Henry Thompson; Paul V. Biron et al. W3C. 5 April 2012. W3C Recommendation. URL: https://www.w3.org/TR/xmlschema11-2/

B.2 Informative references

[COOL-URIS]
Cool URIs for the Semantic Web. Leo Sauermann; Richard Cyganiak. December 2008. Interest Group Note. URL: https://www.w3.org/TR/cooluris/
[DID-KEY]
The did:key Method. Manu Sporny; Dmitri Zagidulin; Dave Longley. 09 June 2020. unofficial. URL: https://w3c-ccg.github.io/did-method-key/
[DID-PEER]
Peer DID Method Specification. Oskar Deventer; Christian Lundkvist; Márton Csernai; Kyle Den Hartog; Markus Sabadello; Sam Curren; Dan Gisolfi; Mike Varley; Sven Hammann; John Jordan; Lovesh Harchandani; Devin Fisher; Tobias Looker; Brent Zundel; Stephen Curran. 10 July 2020. W3C Editor's Draft. URL: https://identity.foundation/peer-did-method-spec/
[DID-SPEC-REGISTRIES]
Decentralized Identifier Extensions. Manu Sporny; Markus Sabadello. W3C. 19 November 2024. W3C Working Group Note. URL: https://www.w3.org/TR/did-extensions/
[KERI]
Key Event Receipt Infrastructure (KERI). Samuel M. Smith. July 2019. URL: https://arxiv.org/abs/1907.02143
[RFC3339]
Date and Time on the Internet: Timestamps. G. Klyne; C. Newman. IETF. July 2002. Proposed Standard. URL: https://www.rfc-editor.org/rfc/rfc3339