did-resolver
Advanced tools
Comparing version 2.2.0 to 3.0.0
@@ -0,1 +1,14 @@ | ||
# [3.0.0](https://github.com/decentralized-identity/did-resolver/compare/2.2.0...3.0.0) (2021-03-02) | ||
### Features | ||
* update resolve method signature to match did core spec ([#82](https://github.com/decentralized-identity/did-resolver/issues/82)) ([313e685](https://github.com/decentralized-identity/did-resolver/commit/313e6858b2819dd9c95b443995b39ed8fed1d678)), closes [#79](https://github.com/decentralized-identity/did-resolver/issues/79) | ||
### BREAKING CHANGES | ||
* the `Resolver` and `DIDResolver` data types have been upgraded. | ||
To use a legacy resolver that simply returns a `DIDDocument`, please register it under the `options.legacyResolvers` constructor param | ||
# [2.2.0](https://github.com/decentralized-identity/did-resolver/compare/2.1.2...2.2.0) (2021-02-26) | ||
@@ -2,0 +15,0 @@ |
@@ -0,24 +1,42 @@ | ||
export interface DIDResolutionResult { | ||
didResolutionMetadata: DIDResolutionMetadata; | ||
didDocument: DIDDocument | null; | ||
didDocumentMetadata: DIDDocumentMetadata; | ||
} | ||
export interface DIDResolutionOptions { | ||
accept?: string; | ||
[x: string]: any; | ||
} | ||
export interface DIDResolutionMetadata { | ||
contentType?: string; | ||
error?: 'invalidDid' | 'notFound' | 'representationNotSupported' | 'unsupportedDidMethod' | string; | ||
[x: string]: any; | ||
} | ||
export interface DIDDocumentMetadata { | ||
created?: string; | ||
updated?: string; | ||
deactivated?: boolean; | ||
versionId?: string; | ||
nextUpdate?: string; | ||
nextVersionId?: string; | ||
equivalentId?: string; | ||
canonicalId?: string; | ||
[x: string]: any; | ||
} | ||
export interface DIDDocument { | ||
'@context': 'https://w3id.org/did/v1' | string | string[]; | ||
'@context'?: 'https://w3id.org/did/v1' | string | string[]; | ||
id: string; | ||
publicKey: PublicKey[]; | ||
authentication?: (string | PublicKey | Authentication)[]; | ||
/** | ||
* @deprecated This does not appear in the did-core spec | ||
*/ | ||
uportProfile?: any; | ||
alsoKnownAs?: string[]; | ||
controller?: string | string[]; | ||
verificationMethod?: VerificationMethod[]; | ||
authentication?: (string | VerificationMethod)[]; | ||
assertionMethod?: (string | VerificationMethod)[]; | ||
keyAgreement?: (string | VerificationMethod)[]; | ||
capabilityInvocation?: (string | VerificationMethod)[]; | ||
capabilityDelegation?: (string | VerificationMethod)[]; | ||
service?: ServiceEndpoint[]; | ||
/** | ||
* @deprecated this property has been removed from the did-core spec | ||
* @deprecated | ||
*/ | ||
created?: string; | ||
/** | ||
* @deprecated this property has been removed from the did-core spec | ||
*/ | ||
updated?: string; | ||
/** | ||
* @deprecated this property has been removed from the did-core spec | ||
*/ | ||
proof?: LinkedDataProof; | ||
keyAgreement?: (string | PublicKey)[]; | ||
publicKey?: VerificationMethod[]; | ||
} | ||
@@ -45,27 +63,12 @@ export interface ServiceEndpoint { | ||
} | ||
export interface PublicKey { | ||
export interface VerificationMethod { | ||
id: string; | ||
type: string; | ||
controller: string; | ||
ethereumAddress?: string; | ||
publicKeyBase64?: string; | ||
publicKeyBase58?: string; | ||
publicKeyJwk?: JsonWebKey; | ||
publicKeyHex?: string; | ||
publicKeyPem?: string; | ||
publicKeyJwk?: JsonWebKey; | ||
blockchainAccountId?: string; | ||
ethereumAddress?: string; | ||
} | ||
/** | ||
* @deprecated The `authentication` array should be an array of strings or `PublicKey` | ||
*/ | ||
export interface Authentication { | ||
type: string; | ||
publicKey: string; | ||
} | ||
export interface LinkedDataProof { | ||
type: string; | ||
created: string; | ||
creator: string; | ||
nonce: string; | ||
signatureValue: string; | ||
} | ||
export interface Params { | ||
@@ -84,17 +87,26 @@ [index: string]: string; | ||
} | ||
export declare type DIDResolver = (did: string, parsed: ParsedDID, resolver: Resolver) => Promise<null | DIDDocument>; | ||
export declare type WrappedResolver = () => Promise<null | DIDDocument>; | ||
export declare type DIDCache = (parsed: ParsedDID, resolve: WrappedResolver) => Promise<null | DIDDocument>; | ||
export declare type DIDResolver = (did: string, parsed: ParsedDID, resolver: Resolver, options: DIDResolutionOptions) => Promise<DIDResolutionResult>; | ||
export declare type WrappedResolver = () => Promise<DIDResolutionResult>; | ||
export declare type DIDCache = (parsed: ParsedDID, resolve: WrappedResolver) => Promise<DIDResolutionResult>; | ||
export declare type LegacyDIDResolver = (did: string, parsed: ParsedDID, resolver: Resolver) => Promise<DIDDocument>; | ||
interface ResolverRegistry { | ||
[index: string]: DIDResolver; | ||
} | ||
interface LegacyResolverRegistry { | ||
[index: string]: LegacyDIDResolver; | ||
} | ||
interface ResolverOptions { | ||
cache?: DIDCache | boolean | undefined; | ||
legacyResolvers?: LegacyResolverRegistry; | ||
} | ||
export declare function inMemoryCache(): DIDCache; | ||
export declare function noCache(parsed: ParsedDID, resolve: WrappedResolver): Promise<null | DIDDocument>; | ||
export declare function parse(didUrl: string): ParsedDID; | ||
export declare function noCache(parsed: ParsedDID, resolve: WrappedResolver): Promise<DIDResolutionResult>; | ||
export declare function parse(didUrl: string): ParsedDID | null; | ||
export declare function wrapLegacyResolver(resolve: LegacyDIDResolver): DIDResolver; | ||
export declare class Resolver { | ||
private registry; | ||
private cache; | ||
constructor(registry?: ResolverRegistry, cache?: DIDCache | boolean | undefined); | ||
resolve(didUrl: string): Promise<DIDDocument>; | ||
constructor(registry?: ResolverRegistry, options?: ResolverOptions); | ||
resolve(didUrl: string, options?: DIDResolutionOptions): Promise<DIDResolutionResult>; | ||
} | ||
export {}; |
@@ -1,2 +0,2 @@ | ||
function r(r,e){(null==e||e>r.length)&&(e=r.length);for(var t=0,n=new Array(e);t<e;t++)n[t]=r[t];return n}function e(){var r=new Map;return function(e,t){try{var n,o=function(o){if(n)return o;var i=r.get(e.did);return void 0!==i?i:Promise.resolve(t()).then(function(t){return null!==t&&r.set(e.did,t),t})},i=function(){if(e.params&&"true"===e.params["no-cache"])return n=1,Promise.resolve(t())}();return Promise.resolve(i&&i.then?i.then(o):o(i))}catch(r){return Promise.reject(r)}}}function t(r,e){return e()}var n=new RegExp("^did:([a-zA-Z0-9_]+):([a-zA-Z0-9_.-]+(:[a-zA-Z0-9_.-]+)*)((;[a-zA-Z0-9_.:%-]+=[a-zA-Z0-9_.:%-]*)*)(/[^#?]*)?([?][^#]*)?(#.*)?$");function o(e){if(""===e||!e)throw new Error("Missing DID");var t=e.match(n);if(t){var o={did:"did:"+t[1]+":"+t[2],method:t[1],id:t[2],didUrl:e};if(t[4]){var i=t[4].slice(1).split(";");o.params={};for(var a,u=function(e,t){var n;if("undefined"==typeof Symbol||null==e[Symbol.iterator]){if(Array.isArray(e)||(n=function(e,t){if(e){if("string"==typeof e)return r(e,t);var n=Object.prototype.toString.call(e).slice(8,-1);return"Object"===n&&e.constructor&&(n=e.constructor.name),"Map"===n||"Set"===n?Array.from(e):"Arguments"===n||/^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)?r(e,t):void 0}}(e))){n&&(e=n);var o=0;return function(){return o>=e.length?{done:!0}:{done:!1,value:e[o++]}}}throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.")}return(n=e[Symbol.iterator]()).next.bind(n)}(i);!(a=u()).done;){var c=a.value.split("=");o.params[c[0]]=c[1]}}return t[6]&&(o.path=t[6]),t[7]&&(o.query=t[7].slice(1)),t[8]&&(o.fragment=t[8].slice(1)),o}throw new Error("Invalid DID "+e)}var i=function(){function r(r,n){void 0===r&&(r={}),this.registry=r,this.cache=!0===n?e():n||t}return r.prototype.resolve=function(r){try{var e,t=this,n=function(r){if(e)return r;throw new Error("Unsupported DID method: '"+i.method+"'")},i=o(r),a=t.registry[i.method],u=function(){if(a)return Promise.resolve(t.cache(i,function(){return a(i.did,i,t)})).then(function(r){if(null==r)throw new Error("resolver returned null for "+i.did);return e=1,r})}();return Promise.resolve(u&&u.then?u.then(n):n(u))}catch(r){return Promise.reject(r)}},r}();export{i as Resolver,e as inMemoryCache,t as noCache,o as parse}; | ||
function r(){return(r=Object.assign||function(r){for(var e=1;e<arguments.length;e++){var t=arguments[e];for(var n in t)Object.prototype.hasOwnProperty.call(t,n)&&(r[n]=t[n])}return r}).apply(this,arguments)}function e(r,e){(null==e||e>r.length)&&(e=r.length);for(var t=0,n=new Array(e);t<e;t++)n[t]=r[t];return n}function t(){var r=new Map;return function(e,t){try{var n,o=function(o){if(n)return o;var i=r.get(e.didUrl);return void 0!==i?i:Promise.resolve(t()).then(function(t){var n;return"notFound"!==(null==(n=t.didResolutionMetadata)?void 0:n.error)&&r.set(e.didUrl,t),t})},i=function(){if(e.params&&"true"===e.params["no-cache"])return n=1,Promise.resolve(t())}();return Promise.resolve(i&&i.then?i.then(o):o(i))}catch(r){return Promise.reject(r)}}}function n(r,e){return e()}var o=new RegExp("^did:([a-zA-Z0-9_]+):([a-zA-Z0-9_.-]+(:[a-zA-Z0-9_.-]+)*)((;[a-zA-Z0-9_.:%-]+=[a-zA-Z0-9_.:%-]*)*)(/[^#?]*)?([?][^#]*)?(#.*)?$");function i(r){if(""===r||!r)return null;var t=r.match(o);if(t){var n={did:"did:"+t[1]+":"+t[2],method:t[1],id:t[2],didUrl:r};if(t[4]){var i=t[4].slice(1).split(";");n.params={};for(var a,u=function(r,t){var n;if("undefined"==typeof Symbol||null==r[Symbol.iterator]){if(Array.isArray(r)||(n=function(r,t){if(r){if("string"==typeof r)return e(r,t);var n=Object.prototype.toString.call(r).slice(8,-1);return"Object"===n&&r.constructor&&(n=r.constructor.name),"Map"===n||"Set"===n?Array.from(r):"Arguments"===n||/^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)?e(r,t):void 0}}(r))){n&&(r=n);var o=0;return function(){return o>=r.length?{done:!0}:{done:!1,value:r[o++]}}}throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.")}return(n=r[Symbol.iterator]()).next.bind(n)}(i);!(a=u()).done;){var c=a.value.split("=");n.params[c[0]]=c[1]}}return t[6]&&(n.path=t[6]),t[7]&&(n.query=t[7].slice(1)),t[8]&&(n.fragment=t[8].slice(1)),n}return null}var a={didResolutionMetadata:{},didDocument:null,didDocumentMetadata:{}};function u(e){return function(t,n,o,i){try{return Promise.resolve(function(i,u){try{var c=Promise.resolve(e(t,n,o)).then(function(e){return r({},a,{didResolutionMetadata:{contentType:"application/did+ld+json"},didDocument:e})})}catch(r){return u(r)}return c&&c.then?c.then(void 0,u):c}(0,function(e){return r({},a,{didResolutionMetadata:{error:"notFound",message:e.toString()}})}))}catch(r){return Promise.reject(r)}}}var c=function(){function e(r,e){var o=this;void 0===r&&(r={}),void 0===e&&(e={}),this.registry=r,this.cache=!0===e.cache?t():e.cache||n,e.legacyResolvers&&Object.keys(e.legacyResolvers).map(function(r){o.registry[r]||(o.registry[r]=u(e.legacyResolvers[r]))})}return e.prototype.resolve=function(e,t){void 0===t&&(t={});try{var n=this,o=i(e);if(null===o)return Promise.resolve(r({},a,{didResolutionMetadata:{error:"invalidDid"}}));var u=n.registry[o.method];return Promise.resolve(u?n.cache(o,function(){return u(o.did,o,n,t)}):r({},a,{didResolutionMetadata:{error:"unsupportedDidMethod"}}))}catch(r){return Promise.reject(r)}},e}();export{c as Resolver,t as inMemoryCache,n as noCache,i as parse,u as wrapLegacyResolver}; | ||
//# sourceMappingURL=resolver.esm.js.map |
@@ -1,2 +0,2 @@ | ||
function r(r,e){(null==e||e>r.length)&&(e=r.length);for(var t=0,n=new Array(e);t<e;t++)n[t]=r[t];return n}function e(){var r=new Map;return function(e,t){try{var n,o=function(o){if(n)return o;var i=r.get(e.did);return void 0!==i?i:Promise.resolve(t()).then(function(t){return null!==t&&r.set(e.did,t),t})},i=function(){if(e.params&&"true"===e.params["no-cache"])return n=1,Promise.resolve(t())}();return Promise.resolve(i&&i.then?i.then(o):o(i))}catch(r){return Promise.reject(r)}}}function t(r,e){return e()}var n=new RegExp("^did:([a-zA-Z0-9_]+):([a-zA-Z0-9_.-]+(:[a-zA-Z0-9_.-]+)*)((;[a-zA-Z0-9_.:%-]+=[a-zA-Z0-9_.:%-]*)*)(/[^#?]*)?([?][^#]*)?(#.*)?$");function o(e){if(""===e||!e)throw new Error("Missing DID");var t=e.match(n);if(t){var o={did:"did:"+t[1]+":"+t[2],method:t[1],id:t[2],didUrl:e};if(t[4]){var i=t[4].slice(1).split(";");o.params={};for(var a,u=function(e,t){var n;if("undefined"==typeof Symbol||null==e[Symbol.iterator]){if(Array.isArray(e)||(n=function(e,t){if(e){if("string"==typeof e)return r(e,t);var n=Object.prototype.toString.call(e).slice(8,-1);return"Object"===n&&e.constructor&&(n=e.constructor.name),"Map"===n||"Set"===n?Array.from(e):"Arguments"===n||/^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)?r(e,t):void 0}}(e))){n&&(e=n);var o=0;return function(){return o>=e.length?{done:!0}:{done:!1,value:e[o++]}}}throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.")}return(n=e[Symbol.iterator]()).next.bind(n)}(i);!(a=u()).done;){var s=a.value.split("=");o.params[s[0]]=s[1]}}return t[6]&&(o.path=t[6]),t[7]&&(o.query=t[7].slice(1)),t[8]&&(o.fragment=t[8].slice(1)),o}throw new Error("Invalid DID "+e)}exports.Resolver=function(){function r(r,n){void 0===r&&(r={}),this.registry=r,this.cache=!0===n?e():n||t}return r.prototype.resolve=function(r){try{var e,t=this,n=function(r){if(e)return r;throw new Error("Unsupported DID method: '"+i.method+"'")},i=o(r),a=t.registry[i.method],u=function(){if(a)return Promise.resolve(t.cache(i,function(){return a(i.did,i,t)})).then(function(r){if(null==r)throw new Error("resolver returned null for "+i.did);return e=1,r})}();return Promise.resolve(u&&u.then?u.then(n):n(u))}catch(r){return Promise.reject(r)}},r}(),exports.inMemoryCache=e,exports.noCache=t,exports.parse=o; | ||
function r(){return(r=Object.assign||function(r){for(var e=1;e<arguments.length;e++){var t=arguments[e];for(var n in t)Object.prototype.hasOwnProperty.call(t,n)&&(r[n]=t[n])}return r}).apply(this,arguments)}function e(r,e){(null==e||e>r.length)&&(e=r.length);for(var t=0,n=new Array(e);t<e;t++)n[t]=r[t];return n}function t(){var r=new Map;return function(e,t){try{var n,o=function(o){if(n)return o;var i=r.get(e.didUrl);return void 0!==i?i:Promise.resolve(t()).then(function(t){var n;return"notFound"!==(null==(n=t.didResolutionMetadata)?void 0:n.error)&&r.set(e.didUrl,t),t})},i=function(){if(e.params&&"true"===e.params["no-cache"])return n=1,Promise.resolve(t())}();return Promise.resolve(i&&i.then?i.then(o):o(i))}catch(r){return Promise.reject(r)}}}function n(r,e){return e()}var o=new RegExp("^did:([a-zA-Z0-9_]+):([a-zA-Z0-9_.-]+(:[a-zA-Z0-9_.-]+)*)((;[a-zA-Z0-9_.:%-]+=[a-zA-Z0-9_.:%-]*)*)(/[^#?]*)?([?][^#]*)?(#.*)?$");function i(r){if(""===r||!r)return null;var t=r.match(o);if(t){var n={did:"did:"+t[1]+":"+t[2],method:t[1],id:t[2],didUrl:r};if(t[4]){var i=t[4].slice(1).split(";");n.params={};for(var a,u=function(r,t){var n;if("undefined"==typeof Symbol||null==r[Symbol.iterator]){if(Array.isArray(r)||(n=function(r,t){if(r){if("string"==typeof r)return e(r,t);var n=Object.prototype.toString.call(r).slice(8,-1);return"Object"===n&&r.constructor&&(n=r.constructor.name),"Map"===n||"Set"===n?Array.from(r):"Arguments"===n||/^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)?e(r,t):void 0}}(r))){n&&(r=n);var o=0;return function(){return o>=r.length?{done:!0}:{done:!1,value:r[o++]}}}throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.")}return(n=r[Symbol.iterator]()).next.bind(n)}(i);!(a=u()).done;){var s=a.value.split("=");n.params[s[0]]=s[1]}}return t[6]&&(n.path=t[6]),t[7]&&(n.query=t[7].slice(1)),t[8]&&(n.fragment=t[8].slice(1)),n}return null}var a={didResolutionMetadata:{},didDocument:null,didDocumentMetadata:{}};function u(e){return function(t,n,o,i){try{return Promise.resolve(function(i,u){try{var s=Promise.resolve(e(t,n,o)).then(function(e){return r({},a,{didResolutionMetadata:{contentType:"application/did+ld+json"},didDocument:e})})}catch(r){return u(r)}return s&&s.then?s.then(void 0,u):s}(0,function(e){return r({},a,{didResolutionMetadata:{error:"notFound",message:e.toString()}})}))}catch(r){return Promise.reject(r)}}}exports.Resolver=function(){function e(r,e){var o=this;void 0===r&&(r={}),void 0===e&&(e={}),this.registry=r,this.cache=!0===e.cache?t():e.cache||n,e.legacyResolvers&&Object.keys(e.legacyResolvers).map(function(r){o.registry[r]||(o.registry[r]=u(e.legacyResolvers[r]))})}return e.prototype.resolve=function(e,t){void 0===t&&(t={});try{var n=this,o=i(e);if(null===o)return Promise.resolve(r({},a,{didResolutionMetadata:{error:"invalidDid"}}));var u=n.registry[o.method];return Promise.resolve(u?n.cache(o,function(){return u(o.did,o,n,t)}):r({},a,{didResolutionMetadata:{error:"unsupportedDidMethod"}}))}catch(r){return Promise.reject(r)}},e}(),exports.inMemoryCache=t,exports.noCache=n,exports.parse=i,exports.wrapLegacyResolver=u; | ||
//# sourceMappingURL=resolver.js.map |
@@ -1,2 +0,2 @@ | ||
function r(){const r=new Map;return async(t,n)=>{if(t.params&&"true"===t.params["no-cache"])return await n();const e=r.get(t.did);if(void 0!==e)return e;const i=await n();return null!==i&&r.set(t.did,i),i}}function t(r,t){return t()}const n=new RegExp("^did:([a-zA-Z0-9_]+):([a-zA-Z0-9_.-]+(:[a-zA-Z0-9_.-]+)*)((;[a-zA-Z0-9_.:%-]+=[a-zA-Z0-9_.:%-]*)*)(/[^#?]*)?([?][^#]*)?(#.*)?$");function e(r){if(""===r||!r)throw new Error("Missing DID");const t=r.match(n);if(t){const n={did:`did:${t[1]}:${t[2]}`,method:t[1],id:t[2],didUrl:r};if(t[4]){const r=t[4].slice(1).split(";");n.params={};for(const t of r){const r=t.split("=");n.params[r[0]]=r[1]}}return t[6]&&(n.path=t[6]),t[7]&&(n.query=t[7].slice(1)),t[8]&&(n.fragment=t[8].slice(1)),n}throw new Error(`Invalid DID ${r}`)}class i{constructor(n={},e){this.registry=n,this.cache=!0===e?r():e||t}async resolve(r){const t=e(r),n=this.registry[t.method];if(n){const r=await this.cache(t,()=>n(t.did,t,this));if(null==r)throw new Error(`resolver returned null for ${t.did}`);return r}throw new Error(`Unsupported DID method: '${t.method}'`)}}export{i as Resolver,r as inMemoryCache,t as noCache,e as parse}; | ||
function t(){return(t=Object.assign||function(t){for(var e=1;e<arguments.length;e++){var r=arguments[e];for(var n in r)Object.prototype.hasOwnProperty.call(r,n)&&(t[n]=r[n])}return t}).apply(this,arguments)}function e(){const t=new Map;return async(e,r)=>{var n;if(e.params&&"true"===e.params["no-cache"])return await r();const a=t.get(e.didUrl);if(void 0!==a)return a;const i=await r();return"notFound"!==(null==(n=i.didResolutionMetadata)?void 0:n.error)&&t.set(e.didUrl,i),i}}function r(t,e){return e()}const n=new RegExp("^did:([a-zA-Z0-9_]+):([a-zA-Z0-9_.-]+(:[a-zA-Z0-9_.-]+)*)((;[a-zA-Z0-9_.:%-]+=[a-zA-Z0-9_.:%-]*)*)(/[^#?]*)?([?][^#]*)?(#.*)?$");function a(t){if(""===t||!t)return null;const e=t.match(n);if(e){const r={did:`did:${e[1]}:${e[2]}`,method:e[1],id:e[2],didUrl:t};if(e[4]){const t=e[4].slice(1).split(";");r.params={};for(const e of t){const t=e.split("=");r.params[t[0]]=t[1]}}return e[6]&&(r.path=e[6]),e[7]&&(r.query=e[7].slice(1)),e[8]&&(r.fragment=e[8].slice(1)),r}return null}const i={didResolutionMetadata:{},didDocument:null,didDocumentMetadata:{}};function o(e){return async(r,n,a,o)=>{try{const o=await e(r,n,a);return t({},i,{didResolutionMetadata:{contentType:"application/did+ld+json"},didDocument:o})}catch(e){return t({},i,{didResolutionMetadata:{error:"notFound",message:e.toString()}})}}}class s{constructor(t={},n={}){this.registry=t,this.cache=!0===n.cache?e():n.cache||r,n.legacyResolvers&&Object.keys(n.legacyResolvers).map(t=>{this.registry[t]||(this.registry[t]=o(n.legacyResolvers[t]))})}async resolve(e,r={}){const n=a(e);if(null===n)return t({},i,{didResolutionMetadata:{error:"invalidDid"}});const o=this.registry[n.method];return o?this.cache(n,()=>o(n.did,n,this,r)):t({},i,{didResolutionMetadata:{error:"unsupportedDidMethod"}})}}export{s as Resolver,e as inMemoryCache,r as noCache,a as parse,o as wrapLegacyResolver}; | ||
//# sourceMappingURL=resolver.modern.js.map |
@@ -1,2 +0,2 @@ | ||
!function(r,e){"object"==typeof exports&&"undefined"!=typeof module?e(exports):"function"==typeof define&&define.amd?define(["exports"],e):e((r||self).didResolver={})}(this,function(r){function e(r,e){(null==e||e>r.length)&&(e=r.length);for(var t=0,n=new Array(e);t<e;t++)n[t]=r[t];return n}function t(){var r=new Map;return function(e,t){try{var n,o=function(o){if(n)return o;var i=r.get(e.did);return void 0!==i?i:Promise.resolve(t()).then(function(t){return null!==t&&r.set(e.did,t),t})},i=function(){if(e.params&&"true"===e.params["no-cache"])return n=1,Promise.resolve(t())}();return Promise.resolve(i&&i.then?i.then(o):o(i))}catch(r){return Promise.reject(r)}}}function n(r,e){return e()}var o=new RegExp("^did:([a-zA-Z0-9_]+):([a-zA-Z0-9_.-]+(:[a-zA-Z0-9_.-]+)*)((;[a-zA-Z0-9_.:%-]+=[a-zA-Z0-9_.:%-]*)*)(/[^#?]*)?([?][^#]*)?(#.*)?$");function i(r){if(""===r||!r)throw new Error("Missing DID");var t=r.match(o);if(t){var n={did:"did:"+t[1]+":"+t[2],method:t[1],id:t[2],didUrl:r};if(t[4]){var i=t[4].slice(1).split(";");n.params={};for(var a,u=function(r,t){var n;if("undefined"==typeof Symbol||null==r[Symbol.iterator]){if(Array.isArray(r)||(n=function(r,t){if(r){if("string"==typeof r)return e(r,t);var n=Object.prototype.toString.call(r).slice(8,-1);return"Object"===n&&r.constructor&&(n=r.constructor.name),"Map"===n||"Set"===n?Array.from(r):"Arguments"===n||/^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)?e(r,t):void 0}}(r))){n&&(r=n);var o=0;return function(){return o>=r.length?{done:!0}:{done:!1,value:r[o++]}}}throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.")}return(n=r[Symbol.iterator]()).next.bind(n)}(i);!(a=u()).done;){var s=a.value.split("=");n.params[s[0]]=s[1]}}return t[6]&&(n.path=t[6]),t[7]&&(n.query=t[7].slice(1)),t[8]&&(n.fragment=t[8].slice(1)),n}throw new Error("Invalid DID "+r)}r.Resolver=function(){function r(r,e){void 0===r&&(r={}),this.registry=r,this.cache=!0===e?t():e||n}return r.prototype.resolve=function(r){try{var e,t=this,n=function(r){if(e)return r;throw new Error("Unsupported DID method: '"+o.method+"'")},o=i(r),a=t.registry[o.method],u=function(){if(a)return Promise.resolve(t.cache(o,function(){return a(o.did,o,t)})).then(function(r){if(null==r)throw new Error("resolver returned null for "+o.did);return e=1,r})}();return Promise.resolve(u&&u.then?u.then(n):n(u))}catch(r){return Promise.reject(r)}},r}(),r.inMemoryCache=t,r.noCache=n,r.parse=i}); | ||
!function(e,r){"object"==typeof exports&&"undefined"!=typeof module?r(exports):"function"==typeof define&&define.amd?define(["exports"],r):r((e||self).didResolver={})}(this,function(e){function r(){return(r=Object.assign||function(e){for(var r=1;r<arguments.length;r++){var t=arguments[r];for(var n in t)Object.prototype.hasOwnProperty.call(t,n)&&(e[n]=t[n])}return e}).apply(this,arguments)}function t(e,r){(null==r||r>e.length)&&(r=e.length);for(var t=0,n=new Array(r);t<r;t++)n[t]=e[t];return n}function n(){var e=new Map;return function(r,t){try{var n,o=function(o){if(n)return o;var i=e.get(r.didUrl);return void 0!==i?i:Promise.resolve(t()).then(function(t){var n;return"notFound"!==(null==(n=t.didResolutionMetadata)?void 0:n.error)&&e.set(r.didUrl,t),t})},i=function(){if(r.params&&"true"===r.params["no-cache"])return n=1,Promise.resolve(t())}();return Promise.resolve(i&&i.then?i.then(o):o(i))}catch(e){return Promise.reject(e)}}}function o(e,r){return r()}var i=new RegExp("^did:([a-zA-Z0-9_]+):([a-zA-Z0-9_.-]+(:[a-zA-Z0-9_.-]+)*)((;[a-zA-Z0-9_.:%-]+=[a-zA-Z0-9_.:%-]*)*)(/[^#?]*)?([?][^#]*)?(#.*)?$");function a(e){if(""===e||!e)return null;var r=e.match(i);if(r){var n={did:"did:"+r[1]+":"+r[2],method:r[1],id:r[2],didUrl:e};if(r[4]){var o=r[4].slice(1).split(";");n.params={};for(var a,u=function(e,r){var n;if("undefined"==typeof Symbol||null==e[Symbol.iterator]){if(Array.isArray(e)||(n=function(e,r){if(e){if("string"==typeof e)return t(e,r);var n=Object.prototype.toString.call(e).slice(8,-1);return"Object"===n&&e.constructor&&(n=e.constructor.name),"Map"===n||"Set"===n?Array.from(e):"Arguments"===n||/^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)?t(e,r):void 0}}(e))){n&&(e=n);var o=0;return function(){return o>=e.length?{done:!0}:{done:!1,value:e[o++]}}}throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.")}return(n=e[Symbol.iterator]()).next.bind(n)}(o);!(a=u()).done;){var d=a.value.split("=");n.params[d[0]]=d[1]}}return r[6]&&(n.path=r[6]),r[7]&&(n.query=r[7].slice(1)),r[8]&&(n.fragment=r[8].slice(1)),n}return null}var u={didResolutionMetadata:{},didDocument:null,didDocumentMetadata:{}};function d(e){return function(t,n,o,i){try{return Promise.resolve(function(i,a){try{var d=Promise.resolve(e(t,n,o)).then(function(e){return r({},u,{didResolutionMetadata:{contentType:"application/did+ld+json"},didDocument:e})})}catch(e){return a(e)}return d&&d.then?d.then(void 0,a):d}(0,function(e){return r({},u,{didResolutionMetadata:{error:"notFound",message:e.toString()}})}))}catch(e){return Promise.reject(e)}}}e.Resolver=function(){function e(e,r){var t=this;void 0===e&&(e={}),void 0===r&&(r={}),this.registry=e,this.cache=!0===r.cache?n():r.cache||o,r.legacyResolvers&&Object.keys(r.legacyResolvers).map(function(e){t.registry[e]||(t.registry[e]=d(r.legacyResolvers[e]))})}return e.prototype.resolve=function(e,t){void 0===t&&(t={});try{var n=this,o=a(e);if(null===o)return Promise.resolve(r({},u,{didResolutionMetadata:{error:"invalidDid"}}));var i=n.registry[o.method];return Promise.resolve(i?n.cache(o,function(){return i(o.did,o,n,t)}):r({},u,{didResolutionMetadata:{error:"unsupportedDidMethod"}}))}catch(e){return Promise.reject(e)}},e}(),e.inMemoryCache=n,e.noCache=o,e.parse=a,e.wrapLegacyResolver=d}); | ||
//# sourceMappingURL=resolver.umd.js.map |
{ | ||
"name": "did-resolver", | ||
"version": "2.2.0", | ||
"version": "3.0.0", | ||
"description": "Resolve DID documents", | ||
@@ -33,4 +33,4 @@ "main": "lib/resolver.js", | ||
"devDependencies": { | ||
"@commitlint/cli": "12.0.0", | ||
"@commitlint/config-conventional": "12.0.0", | ||
"@commitlint/cli": "12.0.1", | ||
"@commitlint/config-conventional": "12.0.1", | ||
"@semantic-release/changelog": "5.0.1", | ||
@@ -45,3 +45,3 @@ "@semantic-release/git": "9.0.0", | ||
"regenerator-runtime": "0.13.7", | ||
"semantic-release": "17.3.9", | ||
"semantic-release": "17.4.0", | ||
"ts-jest": "26.5.2", | ||
@@ -73,4 +73,4 @@ "tslint": "6.1.3", | ||
"resolutions": { | ||
"@babel/core": "7.13.1" | ||
"@babel/core": "7.13.8" | ||
} | ||
} |
@@ -132,13 +132,9 @@ // Copyright 2018 ConsenSys AG | ||
it('fails if non compliant', () => { | ||
expect(() => parse('')).toThrowError(`Missing DID`) | ||
expect(() => parse('did:')).toThrowError(`Invalid DID did:`) | ||
expect(() => parse('did:uport')).toThrowError(`Invalid DID did:uport`) | ||
expect(() => parse('did:uport:')).toThrowError(`Invalid DID did:uport:`) | ||
expect(() => parse('did:uport:1234_12313***')).toThrowError( | ||
`Invalid DID did:uport:1234_12313***` | ||
) | ||
expect(() => parse('2nQtiQG6Cgm1GYTBaaKAgr76uY7iSexUkqX')).toThrowError( | ||
`Invalid DID 2nQtiQG6Cgm1GYTBaaKAgr76uY7iSexUkqX` | ||
) | ||
it('returns null if non compliant', () => { | ||
expect(parse('')).toEqual(null) | ||
expect(parse('did:')).toEqual(null) | ||
expect(parse('did:uport')).toEqual(null) | ||
expect(parse('did:uport:')).toEqual(null) | ||
expect(parse('did:uport:1234_12313***')).toEqual(null) | ||
expect(parse('2nQtiQG6Cgm1GYTBaaKAgr76uY7iSexUkqX')).toEqual(null) | ||
}) | ||
@@ -151,11 +147,14 @@ }) | ||
const mockReturn = Promise.resolve({ | ||
'@context': 'https://w3id.org/did/v1', | ||
id: 'did:mock:abcdef', | ||
publicKey: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
didResolutionMetadata: { contentType: 'application/did+json' }, | ||
didDocument: { | ||
id: 'did:mock:abcdef', | ||
verificationMethod: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
}, | ||
didDocumentMetadata: {} | ||
}) | ||
@@ -166,11 +165,15 @@ beforeAll(() => { | ||
example: async (did, parsed) => ({ | ||
'@context': 'https://w3id.org/did/v1', | ||
id: did, | ||
publicKey: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
didResolutionMetadata: { contentType: 'application/did+ld+json' }, | ||
didDocument: { | ||
'@context': 'https://w3id.org/did/v1', | ||
id: did, | ||
verificationMethod: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
}, | ||
didDocumentMetadata: {} | ||
}), | ||
@@ -183,10 +186,16 @@ mock: mockmethod | ||
await expect( | ||
resolver.resolve('did:borg:2nQtiQG6Cgm1GYTBaaKAgr76uY7iSexUkqX') | ||
).rejects.toEqual(new Error("Unsupported DID method: 'borg'")) | ||
resolver.resolve('did:borg:2nQtiQG6Cgm1GY') | ||
).resolves.toEqual({ | ||
didResolutionMetadata: { error: 'unsupportedDidMethod' }, | ||
didDocument: null, | ||
didDocumentMetadata: {} | ||
}) | ||
}) | ||
it('fails on parse error', async () => { | ||
await expect(resolver.resolve('did:borg:')).rejects.toEqual( | ||
new Error('Invalid DID did:borg:') | ||
) | ||
await expect(resolver.resolve('did:borg:')).resolves.toEqual({ | ||
didResolutionMetadata: { error: 'invalidDid' }, | ||
didDocument: null, | ||
didDocumentMetadata: {} | ||
}) | ||
}) | ||
@@ -196,11 +205,15 @@ | ||
await expect(resolver.resolve('did:example:123456789')).resolves.toEqual({ | ||
'@context': 'https://w3id.org/did/v1', | ||
id: 'did:example:123456789', | ||
publicKey: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
didResolutionMetadata: { contentType: 'application/did+ld+json' }, | ||
didDocument: { | ||
'@context': 'https://w3id.org/did/v1', | ||
id: 'did:example:123456789', | ||
verificationMethod: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
}, | ||
didDocumentMetadata: {} | ||
}) | ||
@@ -210,9 +223,18 @@ }) | ||
it('throws on null document', async () => { | ||
mockmethod = jest.fn().mockReturnValue( | ||
Promise.resolve({ | ||
didResolutionMetadata: { error: 'notFound' }, | ||
didDocument: null, | ||
didDocumentMetadata: {} | ||
}) | ||
) | ||
const nullRes = new Resolver({ | ||
nuller: () => Promise.resolve(null) | ||
nuller: mockmethod | ||
}) | ||
await expect(nullRes.resolve('did:nuller:asdfghjk')).rejects.toEqual( | ||
new Error('resolver returned null for did:nuller:asdfghjk') | ||
) | ||
await expect(nullRes.resolve('did:nuller:asdfghjk')).resolves.toEqual({ | ||
didResolutionMetadata: { error: 'notFound' }, | ||
didDocument: null, | ||
didDocumentMetadata: {} | ||
}) | ||
}) | ||
@@ -229,5 +251,49 @@ | ||
await expect(resolver.resolve('did:mock:abcdef')).resolves.toEqual({ | ||
'@context': 'https://w3id.org/did/v1', | ||
didResolutionMetadata: { contentType: 'application/did+json' }, | ||
didDocument: { | ||
id: 'did:mock:abcdef', | ||
verificationMethod: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
}, | ||
didDocumentMetadata: {} | ||
}) | ||
await expect(resolver.resolve('did:mock:abcdef')).resolves.toEqual({ | ||
didResolutionMetadata: { contentType: 'application/did+json' }, | ||
didDocument: { | ||
id: 'did:mock:abcdef', | ||
verificationMethod: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
}, | ||
didDocumentMetadata: {} | ||
}) | ||
return expect(mockmethod).toBeCalledTimes(2) | ||
}) | ||
}) | ||
}) | ||
describe('cache=true', () => { | ||
it('should cache', async () => { | ||
mockmethod = jest.fn().mockReturnValue(mockReturn) | ||
resolver = new Resolver( | ||
{ | ||
mock: mockmethod | ||
}, | ||
{ cache: true } | ||
) | ||
await expect(resolver.resolve('did:mock:abcdef')).resolves.toEqual({ | ||
didResolutionMetadata: { contentType: 'application/did+json' }, | ||
didDocument: { | ||
id: 'did:mock:abcdef', | ||
publicKey: [ | ||
verificationMethod: [ | ||
{ | ||
@@ -239,7 +305,10 @@ id: 'owner', | ||
] | ||
}) | ||
await expect(resolver.resolve('did:mock:abcdef')).resolves.toEqual({ | ||
'@context': 'https://w3id.org/did/v1', | ||
}, | ||
didDocumentMetadata: {} | ||
}) | ||
await expect(resolver.resolve('did:mock:abcdef')).resolves.toEqual({ | ||
didResolutionMetadata: { contentType: 'application/did+json' }, | ||
didDocument: { | ||
id: 'did:mock:abcdef', | ||
publicKey: [ | ||
verificationMethod: [ | ||
{ | ||
@@ -251,10 +320,9 @@ id: 'owner', | ||
] | ||
}) | ||
return expect(mockmethod).toBeCalledTimes(2) | ||
}, | ||
didDocumentMetadata: {} | ||
}) | ||
return expect(mockmethod).toBeCalledTimes(1) | ||
}) | ||
}) | ||
describe('cache=true', () => { | ||
it('should cache', async () => { | ||
it('should respect no-cache', async () => { | ||
mockmethod = jest.fn().mockReturnValue(mockReturn) | ||
@@ -265,31 +333,39 @@ resolver = new Resolver( | ||
}, | ||
true | ||
{ cache: true } | ||
) | ||
await expect(resolver.resolve('did:mock:abcdef')).resolves.toEqual({ | ||
'@context': 'https://w3id.org/did/v1', | ||
id: 'did:mock:abcdef', | ||
publicKey: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
didResolutionMetadata: { contentType: 'application/did+json' }, | ||
didDocument: { | ||
id: 'did:mock:abcdef', | ||
verificationMethod: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
}, | ||
didDocumentMetadata: {} | ||
}) | ||
await expect(resolver.resolve('did:mock:abcdef')).resolves.toEqual({ | ||
'@context': 'https://w3id.org/did/v1', | ||
id: 'did:mock:abcdef', | ||
publicKey: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
await expect( | ||
resolver.resolve('did:mock:abcdef;no-cache=true') | ||
).resolves.toEqual({ | ||
didResolutionMetadata: { contentType: 'application/did+json' }, | ||
didDocument: { | ||
id: 'did:mock:abcdef', | ||
verificationMethod: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
}, | ||
didDocumentMetadata: {} | ||
}) | ||
return expect(mockmethod).toBeCalledTimes(1) | ||
return expect(mockmethod).toBeCalledTimes(2) | ||
}) | ||
it('should respect no-cache', async () => { | ||
it('should not cache with different params', async () => { | ||
mockmethod = jest.fn().mockReturnValue(mockReturn) | ||
@@ -300,28 +376,34 @@ resolver = new Resolver( | ||
}, | ||
true | ||
{ cache: true } | ||
) | ||
await expect(resolver.resolve('did:mock:abcdef')).resolves.toEqual({ | ||
'@context': 'https://w3id.org/did/v1', | ||
id: 'did:mock:abcdef', | ||
publicKey: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
didResolutionMetadata: { contentType: 'application/did+json' }, | ||
didDocument: { | ||
id: 'did:mock:abcdef', | ||
verificationMethod: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
}, | ||
didDocumentMetadata: {} | ||
}) | ||
await expect( | ||
resolver.resolve('did:mock:abcdef;no-cache=true') | ||
resolver.resolve('did:mock:abcdef?versionId=2') | ||
).resolves.toEqual({ | ||
'@context': 'https://w3id.org/did/v1', | ||
id: 'did:mock:abcdef', | ||
publicKey: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
didResolutionMetadata: { contentType: 'application/did+json' }, | ||
didDocument: { | ||
id: 'did:mock:abcdef', | ||
verificationMethod: [ | ||
{ | ||
id: 'owner', | ||
controller: '1234', | ||
type: 'xyz' | ||
} | ||
] | ||
}, | ||
didDocumentMetadata: {} | ||
}) | ||
@@ -332,3 +414,9 @@ return expect(mockmethod).toBeCalledTimes(2) | ||
it('should not cache null docs', async () => { | ||
mockmethod = jest.fn().mockReturnValue(null) | ||
mockmethod = jest.fn().mockReturnValue( | ||
Promise.resolve({ | ||
didResolutionMetadata: { error: 'notFound' }, | ||
didDocument: null, | ||
didDocumentMetadata: {} | ||
}) | ||
) | ||
resolver = new Resolver( | ||
@@ -338,11 +426,15 @@ { | ||
}, | ||
true | ||
{ cache: true } | ||
) | ||
await expect(resolver.resolve('did:mock:abcdef')).rejects.toEqual( | ||
new Error('resolver returned null for did:mock:abcdef') | ||
) | ||
await expect(resolver.resolve('did:mock:abcdef')).rejects.toEqual( | ||
new Error('resolver returned null for did:mock:abcdef') | ||
) | ||
await expect(resolver.resolve('did:mock:abcdef')).resolves.toEqual({ | ||
didResolutionMetadata: { error: 'notFound' }, | ||
didDocument: null, | ||
didDocumentMetadata: {} | ||
}) | ||
await expect(resolver.resolve('did:mock:abcdef')).resolves.toEqual({ | ||
didResolutionMetadata: { error: 'notFound' }, | ||
didDocument: null, | ||
didDocumentMetadata: {} | ||
}) | ||
return expect(mockmethod).toBeCalledTimes(2) | ||
@@ -349,0 +441,0 @@ }) |
@@ -15,25 +15,52 @@ // Copyright 2018 ConsenSys AG | ||
export interface DIDResolutionResult { | ||
didResolutionMetadata: DIDResolutionMetadata | ||
didDocument: DIDDocument | null | ||
didDocumentMetadata: DIDDocumentMetadata | ||
} | ||
export interface DIDResolutionOptions { | ||
accept?: string | ||
[x: string]: any | ||
} | ||
export interface DIDResolutionMetadata { | ||
contentType?: string | ||
error?: | ||
| 'invalidDid' | ||
| 'notFound' | ||
| 'representationNotSupported' | ||
| 'unsupportedDidMethod' | ||
| string | ||
[x: string]: any | ||
} | ||
export interface DIDDocumentMetadata { | ||
created?: string | ||
updated?: string | ||
deactivated?: boolean | ||
versionId?: string | ||
nextUpdate?: string | ||
nextVersionId?: string | ||
equivalentId?: string | ||
canonicalId?: string | ||
[x: string]: any | ||
} | ||
export interface DIDDocument { | ||
'@context': 'https://w3id.org/did/v1' | string | string[] | ||
'@context'?: 'https://w3id.org/did/v1' | string | string[] | ||
id: string | ||
publicKey: PublicKey[] | ||
authentication?: (string | PublicKey | Authentication)[] | ||
/** | ||
* @deprecated This does not appear in the did-core spec | ||
*/ | ||
uportProfile?: any | ||
alsoKnownAs?: string[] | ||
controller?: string | string[] | ||
verificationMethod?: VerificationMethod[] | ||
authentication?: (string | VerificationMethod)[] | ||
assertionMethod?: (string | VerificationMethod)[] | ||
keyAgreement?: (string | VerificationMethod)[] | ||
capabilityInvocation?: (string | VerificationMethod)[] | ||
capabilityDelegation?: (string | VerificationMethod)[] | ||
service?: ServiceEndpoint[] | ||
/** | ||
* @deprecated this property has been removed from the did-core spec | ||
* @deprecated | ||
*/ | ||
created?: string | ||
/** | ||
* @deprecated this property has been removed from the did-core spec | ||
*/ | ||
updated?: string | ||
/** | ||
* @deprecated this property has been removed from the did-core spec | ||
*/ | ||
proof?: LinkedDataProof | ||
keyAgreement?: (string | PublicKey)[] | ||
publicKey?: VerificationMethod[] | ||
} | ||
@@ -63,30 +90,13 @@ | ||
export interface PublicKey { | ||
export interface VerificationMethod { | ||
id: string | ||
type: string | ||
controller: string | ||
ethereumAddress?: string | ||
publicKeyBase64?: string | ||
publicKeyBase58?: string | ||
publicKeyJwk?: JsonWebKey | ||
publicKeyHex?: string | ||
publicKeyPem?: string | ||
publicKeyJwk?: JsonWebKey | ||
blockchainAccountId?: string | ||
ethereumAddress?: string | ||
} | ||
/** | ||
* @deprecated The `authentication` array should be an array of strings or `PublicKey` | ||
*/ | ||
export interface Authentication { | ||
type: string | ||
publicKey: string | ||
} | ||
export interface LinkedDataProof { | ||
type: string | ||
created: string | ||
creator: string | ||
nonce: string | ||
signatureValue: string | ||
} | ||
export interface Params { | ||
@@ -110,9 +120,15 @@ [index: string]: string | ||
parsed: ParsedDID, | ||
resolver: Resolver | ||
) => Promise<null | DIDDocument> | ||
export type WrappedResolver = () => Promise<null | DIDDocument> | ||
resolver: Resolver, | ||
options: DIDResolutionOptions | ||
) => Promise<DIDResolutionResult> | ||
export type WrappedResolver = () => Promise<DIDResolutionResult> | ||
export type DIDCache = ( | ||
parsed: ParsedDID, | ||
resolve: WrappedResolver | ||
) => Promise<null | DIDDocument> | ||
) => Promise<DIDResolutionResult> | ||
export type LegacyDIDResolver = ( | ||
did: string, | ||
parsed: ParsedDID, | ||
resolver: Resolver | ||
) => Promise<DIDDocument> | ||
@@ -123,4 +139,13 @@ interface ResolverRegistry { | ||
interface LegacyResolverRegistry { | ||
[index: string]: LegacyDIDResolver | ||
} | ||
interface ResolverOptions { | ||
cache?: DIDCache | boolean | undefined | ||
legacyResolvers?: LegacyResolverRegistry | ||
} | ||
export function inMemoryCache(): DIDCache { | ||
const cache: Map<string, DIDDocument | null> = new Map() | ||
const cache: Map<string, DIDResolutionResult> = new Map() | ||
return async (parsed, resolve) => { | ||
@@ -130,9 +155,9 @@ if (parsed.params && parsed.params['no-cache'] === 'true') | ||
const cached = cache.get(parsed.did) | ||
const cached = cache.get(parsed.didUrl) | ||
if (cached !== undefined) return cached | ||
const doc = await resolve() | ||
if (doc !== null) { | ||
cache.set(parsed.did, doc) | ||
const result = await resolve() | ||
if (result.didResolutionMetadata?.error !== 'notFound') { | ||
cache.set(parsed.didUrl, result) | ||
} | ||
return doc | ||
return result | ||
} | ||
@@ -144,3 +169,3 @@ } | ||
resolve: WrappedResolver | ||
): Promise<null | DIDDocument> { | ||
): Promise<DIDResolutionResult> { | ||
return resolve() | ||
@@ -161,4 +186,4 @@ } | ||
) | ||
export function parse(didUrl: string): ParsedDID { | ||
if (didUrl === '' || !didUrl) throw new Error('Missing DID') | ||
export function parse(didUrl: string): ParsedDID | null { | ||
if (didUrl === '' || !didUrl) return null | ||
const sections = didUrl.match(DID_MATCHER) | ||
@@ -185,5 +210,32 @@ if (sections) { | ||
} | ||
throw new Error(`Invalid DID ${didUrl}`) | ||
return null | ||
} | ||
const EMPTY_RESULT: DIDResolutionResult = { | ||
didResolutionMetadata: {}, | ||
didDocument: null, | ||
didDocumentMetadata: {} | ||
} | ||
export function wrapLegacyResolver(resolve: LegacyDIDResolver): DIDResolver { | ||
return async (did, parsed, resolver, options) => { | ||
try { | ||
const doc = await resolve(did, parsed, resolver) | ||
return { | ||
...EMPTY_RESULT, | ||
didResolutionMetadata: { contentType: 'application/did+ld+json' }, | ||
didDocument: doc | ||
} | ||
} catch (e) { | ||
return { | ||
...EMPTY_RESULT, | ||
didResolutionMetadata: { | ||
error: 'notFound', | ||
message: e.toString() // This is not in spec, nut may be helpful | ||
} | ||
} | ||
} | ||
} | ||
} | ||
export class Resolver { | ||
@@ -193,25 +245,37 @@ private registry: ResolverRegistry | ||
constructor( | ||
registry: ResolverRegistry = {}, | ||
cache?: DIDCache | boolean | undefined | ||
) { | ||
constructor(registry: ResolverRegistry = {}, options: ResolverOptions = {}) { | ||
this.registry = registry | ||
this.cache = cache === true ? inMemoryCache() : cache || noCache | ||
this.cache = | ||
options.cache === true ? inMemoryCache() : options.cache || noCache | ||
if (options.legacyResolvers) { | ||
Object.keys(options.legacyResolvers).map((methodName) => { | ||
if (!this.registry[methodName]) { | ||
this.registry[methodName] = wrapLegacyResolver( | ||
options.legacyResolvers![methodName] | ||
) | ||
} | ||
}) | ||
} | ||
} | ||
async resolve(didUrl: string): Promise<DIDDocument> { | ||
async resolve( | ||
didUrl: string, | ||
options: DIDResolutionOptions = {} | ||
): Promise<DIDResolutionResult> { | ||
const parsed = parse(didUrl) | ||
if (parsed === null) { | ||
return { | ||
...EMPTY_RESULT, | ||
didResolutionMetadata: { error: 'invalidDid' } | ||
} | ||
} | ||
const resolver = this.registry[parsed.method] | ||
if (resolver) { | ||
const doc = await this.cache(parsed, () => | ||
resolver(parsed.did, parsed, this) | ||
) | ||
if (doc == null) { | ||
throw new Error(`resolver returned null for ${parsed.did}`) | ||
} else { | ||
return doc | ||
if (!resolver) { | ||
return { | ||
...EMPTY_RESULT, | ||
didResolutionMetadata: { error: 'unsupportedDidMethod' } | ||
} | ||
} | ||
throw new Error(`Unsupported DID method: '${parsed.method}'`) | ||
return this.cache(parsed, () => resolver(parsed.did, parsed, this, options)) | ||
} | ||
} |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
96009
815