Skip to content

Commit

Permalink
feat: Add new ed25519 2018 signature and spec implementation using tr…
Browse files Browse the repository at this point in the history
…ansmute's TS implementation
  • Loading branch information
nklomp committed Dec 10, 2021
1 parent c990f09 commit ffbe876
Show file tree
Hide file tree
Showing 3 changed files with 270 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
{
"@context": {
"id": "@id",
"type": "@type",
"@protected": true,
"proof": {
"@id": "https://w3id.org/security#proof",
"@type": "@id",
"@container": "@graph"
},
"Ed25519VerificationKey2018": {
"@id": "https://w3id.org/security#Ed25519VerificationKey2018",
"@context": {
"@protected": true,
"id": "@id",
"type": "@type",
"controller": {
"@id": "https://w3id.org/security#controller",
"@type": "@id"
},
"revoked": {
"@id": "https://w3id.org/security#revoked",
"@type": "http://www.w3.org/2001/XMLSchema#dateTime"
},
"publicKeyBase58": {
"@id": "https://w3id.org/security#publicKeyBase58"
}
}
},
"Ed25519Signature2018": {
"@id": "https://w3id.org/security#Ed25519Signature2018",
"@context": {
"@protected": true,
"id": "@id",
"type": "@type",
"challenge": "https://w3id.org/security#challenge",
"created": {
"@id": "http://purl.org/dc/terms/created",
"@type": "http://www.w3.org/2001/XMLSchema#dateTime"
},
"domain": "https://w3id.org/security#domain",
"expires": {
"@id": "https://w3id.org/security#expiration",
"@type": "http://www.w3.org/2001/XMLSchema#dateTime"
},
"nonce": "https://w3id.org/security#nonce",
"proofPurpose": {
"@id": "https://w3id.org/security#proofPurpose",
"@type": "@vocab",
"@context": {
"@protected": true,
"id": "@id",
"type": "@type",
"assertionMethod": {
"@id": "https://w3id.org/security#assertionMethod",
"@type": "@id",
"@container": "@set"
},
"authentication": {
"@id": "https://w3id.org/security#authenticationMethod",
"@type": "@id",
"@container": "@set"
},
"capabilityInvocation": {
"@id": "https://w3id.org/security#capabilityInvocationMethod",
"@type": "@id",
"@container": "@set"
},
"capabilityDelegation": {
"@id": "https://w3id.org/security#capabilityDelegationMethod",
"@type": "@id",
"@container": "@set"
},
"keyAgreement": {
"@id": "https://w3id.org/security#keyAgreementMethod",
"@type": "@id",
"@container": "@set"
}
}
},
"jws": {
"@id": "https://w3id.org/security#jws"
},
"verificationMethod": {
"@id": "https://w3id.org/security#verificationMethod",
"@type": "@id"
}
}
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,93 @@
{
"@context": {
"id": "@id",
"type": "@type",
"@protected": true,
"proof": {
"@id": "https://w3id.org/security#proof",
"@type": "@id",
"@container": "@graph"
},
"Ed25519VerificationKey2020": {
"@id": "https://w3id.org/security#Ed25519VerificationKey2020",
"@context": {
"@protected": true,
"id": "@id",
"type": "@type",
"controller": {
"@id": "https://w3id.org/security#controller",
"@type": "@id"
},
"revoked": {
"@id": "https://w3id.org/security#revoked",
"@type": "http://www.w3.org/2001/XMLSchema#dateTime"
},
"publicKeyMultibase": {
"@id": "https://w3id.org/security#publicKeyMultibase",
"@type": "https://w3id.org/security#multibase"
}
}
},
"Ed25519Signature2020": {
"@id": "https://w3id.org/security#Ed25519Signature2020",
"@context": {
"@protected": true,
"id": "@id",
"type": "@type",
"challenge": "https://w3id.org/security#challenge",
"created": {
"@id": "http://purl.org/dc/terms/created",
"@type": "http://www.w3.org/2001/XMLSchema#dateTime"
},
"domain": "https://w3id.org/security#domain",
"expires": {
"@id": "https://w3id.org/security#expiration",
"@type": "http://www.w3.org/2001/XMLSchema#dateTime"
},
"nonce": "https://w3id.org/security#nonce",
"proofPurpose": {
"@id": "https://w3id.org/security#proofPurpose",
"@type": "@vocab",
"@context": {
"@protected": true,
"id": "@id",
"type": "@type",
"assertionMethod": {
"@id": "https://w3id.org/security#assertionMethod",
"@type": "@id",
"@container": "@set"
},
"authentication": {
"@id": "https://w3id.org/security#authenticationMethod",
"@type": "@id",
"@container": "@set"
},
"capabilityInvocation": {
"@id": "https://w3id.org/security#capabilityInvocationMethod",
"@type": "@id",
"@container": "@set"
},
"capabilityDelegation": {
"@id": "https://w3id.org/security#capabilityDelegationMethod",
"@type": "@id",
"@container": "@set"
},
"keyAgreement": {
"@id": "https://w3id.org/security#keyAgreementMethod",
"@type": "@id",
"@container": "@set"
}
}
},
"proofValue": {
"@id": "https://w3id.org/security#proofValue",
"@type": "https://w3id.org/security#multibase"
},
"verificationMethod": {
"@id": "https://w3id.org/security#verificationMethod",
"@type": "@id"
}
}
}
}
}
86 changes: 86 additions & 0 deletions packages/vc-handler-ld-local/src/suites/Ed25519Signature2018.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
import { encodeJoseBlob } from '@veramo/utils'
import { CredentialPayload, DIDDocument, IAgentContext, IKey, TKeyType, VerifiableCredential } from '@veramo/core'
import suiteContext2018 from 'ed25519-signature-2018-context'
import { Ed25519Signature2018 } from '@transmute/ed25519-signature-2018'
import * as u8a from 'uint8arrays'
import { RequiredAgentMethods, SphereonLdSignature } from '../ld-suites'
import { Ed25519KeyPair } from '@transmute/ed25519-key-pair'

export class SphereonEd25519Signature2018 extends SphereonLdSignature {
constructor() {
super()
// Ensure it is loaded
suiteContext2018?.constants
}

getSupportedVerificationType(): string {
return 'Ed25519VerificationKey2018'
}

getSupportedVeramoKeyType(): TKeyType {
return 'Ed25519'
}

getContext(): string {
return 'https://w3id.org/security/suites/ed25519-2018/v1'
}

getSuiteForSigning(key: IKey, issuerDid: string, verificationMethodId: string, context: IAgentContext<RequiredAgentMethods>): any {
const controller = issuerDid

// DID Key ID
let id = verificationMethodId

const signer = {
// returns a JWS detached
sign: async (args: { data: Uint8Array }): Promise<string> => {
const header = {
alg: 'EdDSA',
b64: false,
crit: ['b64'],
}
const headerString = encodeJoseBlob(header)
const messageBuffer = u8a.concat([u8a.fromString(`${headerString}.`, 'utf-8'), args.data])
const messageString = u8a.toString(messageBuffer, 'base64')
const signature = await context.agent.keyManagerSign({
keyRef: key.kid,
algorithm: 'EdDSA',
data: messageString,
encoding: 'base64',
})
return `${headerString}..${signature}`
// return u8a.fromString(`${headerString}..${signature}`)
},
}

const options = {
id: id,
controller: controller,
publicKey: u8a.fromString(key.publicKeyHex),
signer: () => signer,
type: this.getSupportedVerificationType(),
}

// For now we always go through this route given the multibase key has an invalid header
const verificationKey = new Ed25519KeyPair(options)
// overwrite the signer since we're not passing the private key and transmute doesn't support that behavior
verificationKey.signer = () => signer as any
// verificationKey.type = this.getSupportedVerificationType()

return new Ed25519Signature2018({key: verificationKey, signer: signer })
}

preVerificationCredModification(credential: VerifiableCredential): void {}
getSuiteForVerification(): any {
return new Ed25519Signature2018()
}

preSigningCredModification(credential: CredentialPayload): void {
console.log(credential)
// nothing to do here
}

preDidResolutionModification(didUrl: string, didDoc: DIDDocument): void {
// nothing to do here
}
}

0 comments on commit ffbe876

Please sign in to comment.