@credo-ts/core
Version:
<p align="center"> <br /> <img alt="Credo Logo" src="https://github.com/openwallet-foundation/credo-ts/blob/c7886cb8377ceb8ee4efe8d264211e561a75072d/images/credo-logo.png" height="250px" /> </p> <h1 align="center"><b>Credo - Core</b></h1
192 lines (188 loc) • 8.26 kB
JavaScript
import { TypedArrayEncoder } from "../../../../../utils/TypedArrayEncoder.mjs";
import { MultiBaseEncoder } from "../../../../../utils/MultiBaseEncoder.mjs";
import "../../../../../utils/index.mjs";
import { Ed25519PublicJwk } from "../../../../kms/jwk/kty/okp/Ed25519PublicJwk.mjs";
import { PublicJwk } from "../../../../kms/jwk/PublicJwk.mjs";
import "../../../../kms/index.mjs";
import { CREDENTIALS_CONTEXT_V1_URL, SECURITY_CONTEXT_URL } from "../../../constants.mjs";
import { ED25519_SUITE_CONTEXT_URL_2020 } from "./constants.mjs";
import jsonld_default from "../../libraries/jsonld.mjs";
import { _includesContext } from "../../jsonldUtil.mjs";
import { JwsLinkedDataSignature } from "../JwsLinkedDataSignature.mjs";
import { ed25519Signature2020Context } from "./context2020.mjs";
//#region src/modules/vc/data-integrity/signature-suites/ed25519/Ed25519Signature2020.ts
var Ed25519Signature2020 = class extends JwsLinkedDataSignature {
/**
* @param {object} options - Options hashmap.
*
* Either a `key` OR at least one of `signer`/`verifier` is required.
*
* @param {object} [options.key] - An optional key object (containing an
* `id` property, and either `signer` or `verifier`, depending on the
* intended operation. Useful for when the application is managing keys
* itself (when using a KMS, you never have access to the private key,
* and so should use the `signer` param instead).
* @param {Function} [options.signer] - Signer function that returns an
* object with an async sign() method. This is useful when interfacing
* with a KMS (since you don't get access to the private key and its
* `signer()`, the KMS client gives you only the signer function to use).
* @param {Function} [options.verifier] - Verifier function that returns
* an object with an async `verify()` method. Useful when working with a
* KMS-provided verifier function.
*
* Advanced optional parameters and overrides.
*
* @param {object} [options.proof] - A JSON-LD document with options to use
* for the `proof` node. Any other custom fields can be provided here
* using a context different from security-v2).
* @param {string|Date} [options.date] - Signing date to use if not passed.
* @param {boolean} [options.useNativeCanonize] - Whether to use a native
* canonize algorithm.
*/
constructor(options) {
super({
type: "Ed25519Signature2020",
algorithm: "EdDSA",
LDKeyClass: options.LDKeyClass,
contextUrl: ED25519_SUITE_CONTEXT_URL_2020,
key: options.key,
proof: options.proof,
date: options.date,
useNativeCanonize: options.useNativeCanonize
});
this.requiredKeyType = "Ed25519VerificationKey2020";
}
async assertVerificationMethod(document) {
if (!_includesCompatibleContext({ document })) throw new TypeError(`The '@context' of the verification method (key) MUST contain the context url "${this.contextUrl}".`);
if (!_isEd2020Key(document)) {
const verificationMethodType = jsonld_default.getValues(document, "type")[0];
throw new Error(`Unsupported verification method type '${verificationMethodType}'. Verification method type MUST be 'Ed25519VerificationKey2020'.`);
}
if (_isEd2020Key(document) && !_includesEd2020Context(document)) throw new Error(`For verification method type 'Ed25519VerificationKey2020' the '@context' MUST contain the context url "${ED25519_SUITE_CONTEXT_URL_2020}".`);
if (document.revoked !== void 0) throw new Error("The verification method has been revoked.");
}
async getVerificationMethod(options) {
let verificationMethod = await super.getVerificationMethod({
proof: options.proof,
documentLoader: options.documentLoader
});
if (_isEd2020Key(verificationMethod) && _includesEd2020Context(verificationMethod)) {
const publicJwk = PublicJwk.fromFingerprint(verificationMethod.publicKeyMultibase);
if (!publicJwk.is(Ed25519PublicJwk)) throw new Error("Expected multibase key to be of type Ed25519.");
verificationMethod.type = "Ed25519VerificationKey2018";
verificationMethod = {
...verificationMethod,
publicKeyMultibase: void 0,
publicKeyBase58: TypedArrayEncoder.toBase58(publicJwk.publicKey.publicKey)
};
}
return verificationMethod;
}
/**
* Ensures the document to be signed contains the required signature suite
* specific `@context`, by either adding it (if `addSuiteContext` is true),
* or throwing an error if it's missing.
*
* @override
*
* @param {object} options - Options hashmap.
* @param {object} options.document - JSON-LD document to be signed.
* @param {boolean} options.addSuiteContext - Add suite context?
*/
ensureSuiteContext(options) {
if (_includesCompatibleContext({ document: options.document })) return;
super.ensureSuiteContext({
document: options.document,
addSuiteContext: options.addSuiteContext
});
}
/**
* Checks whether a given proof exists in the document.
*
* @override
*
* @param {object} options - Options hashmap.
* @param {object} options.proof - A proof.
* @param {object} options.document - A JSON-LD document.
* @param {object} options.purpose - A jsonld-signatures ProofPurpose
* instance (e.g. AssertionProofPurpose, AuthenticationProofPurpose, etc).
* @param {Function} options.documentLoader - A secure document loader (it is
* recommended to use one that provides static known documents, instead of
* fetching from the web) for returning contexts, controller documents,
* keys, and other relevant URLs needed for the proof.
*
* @returns {Promise<boolean>} Whether a match for the proof was found.
*/
async matchProof(options) {
if (!_includesCompatibleContext({ document: options.document })) return false;
return super.matchProof({
proof: options.proof,
document: options.document,
purpose: options.purpose,
documentLoader: options.documentLoader
});
}
/**
* @param options - Options hashmap.
* @param options.verifyData - The data to sign.
* @param options.proof - A JSON-LD document with options to use
* for the `proof` node. Any other custom fields can be provided here
* using a context different from `security-v2`.
*
* @returns The proof containing the signature value.
*/
async sign(options) {
if (!(this.signer && typeof this.signer.sign === "function")) throw new Error("A signer API has not been specified.");
const signature = await this.signer.sign({ data: options.verifyData });
const encodedSignature = MultiBaseEncoder.encode(signature, "base58btc");
options.proof.proofValue = encodedSignature;
return options.proof;
}
/**
* @param options - Options hashmap.
* @param options.verifyData - The data to verify.
* @param options.verificationMethod - A verification method.
* @param options.proof - The proof to be verified.
*
* @returns Resolves with the verification result.
*/
async verifySignature(options) {
if (!(options.proof.proofValue && typeof options.proof.proofValue === "string")) throw new TypeError("The proof does not include a valid \"proofValue\" property.");
const signature = MultiBaseEncoder.decode(options.proof.proofValue).data;
let { verifier } = this;
if (!verifier) verifier = (await this.LDKeyClass.from(options.verificationMethod)).verifier();
return verifier.verify({
data: options.verifyData,
signature
});
}
};
Ed25519Signature2020.CONTEXT_URL = ED25519_SUITE_CONTEXT_URL_2020;
Ed25519Signature2020.CONTEXT = ed25519Signature2020Context.get(ED25519_SUITE_CONTEXT_URL_2020);
function _includesCompatibleContext(options) {
const hasEd2020 = _includesContext({
document: options.document,
contextUrl: ED25519_SUITE_CONTEXT_URL_2020
});
const hasCred = _includesContext({
document: options.document,
contextUrl: CREDENTIALS_CONTEXT_V1_URL
});
const hasSecV2 = _includesContext({
document: options.document,
contextUrl: SECURITY_CONTEXT_URL
});
return hasEd2020 || hasCred || hasSecV2;
}
function _isEd2020Key(verificationMethod) {
return jsonld_default.hasValue(verificationMethod, "type", "Ed25519VerificationKey2020");
}
function _includesEd2020Context(document) {
return _includesContext({
document,
contextUrl: ED25519_SUITE_CONTEXT_URL_2020
});
}
//#endregion
export { Ed25519Signature2020 };
//# sourceMappingURL=Ed25519Signature2020.mjs.map