Created
December 5, 2019 15:50
-
-
Save dlongley/b19f2723e11d99d2e39d36b6f8ae7e17 to your computer and use it in GitHub Desktop.
panva vs. jsigs detached JWS
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
const jose = require('jose'); | |
const sodium = require('sodium-native'); | |
const base64url = require('base64url-universal'); | |
const key = { | |
kty: 'OKP', | |
crv: 'Ed25519', | |
d: 'nWGxne_9WmC6hEr0kuwsxERJxWl7MmkZcDusAxyuf2A', | |
x: '11qYAYKxCrfVS_7TyWQHOg7hcvPapiMlrwIaaPcHURo' | |
}; | |
test(); | |
async function test() { | |
const data = new Uint8Array([1, 2, 3]); | |
try { | |
const sig1 = await panva(data); | |
console.log('sig1', sig1); | |
const sig2 = await ld(data); | |
console.log('sig2', sig2); | |
if(sig1 !== sig2) { | |
throw new Error('signatures do not match'); | |
} | |
console.log('signatures match!'); | |
} catch(e) { | |
console.error(e); | |
} | |
} | |
async function ld(verifyData) { | |
// JWS header | |
const header = { | |
alg: 'EdDSA', | |
b64: false, | |
crit: ['b64'] | |
}; | |
// create JWS data and sign | |
const encodedHeader = base64url.encode(JSON.stringify(header)); | |
const data = createJws({encodedHeader, verifyData}); | |
const signature = await sign(data); | |
// create detached content signature | |
const encodedSignature = base64url.encode(signature); | |
return encodedHeader + '..' + encodedSignature; | |
} | |
async function panva(data) { | |
const header = { | |
alg: "EdDSA", | |
b64: false, | |
crit: ["b64"] | |
}; | |
let toBeSigned = Buffer.from(data.buffer, data.byteOffset, data.length); | |
const flattened = jose.JWS.sign.flattened( | |
toBeSigned, | |
jose.JWK.asKey(key), | |
header | |
); | |
return flattened.protected + ".." + flattened.signature; | |
} | |
async function sign(data) { | |
const d = base64url.decode(key.d); | |
const x = base64url.decode(key.x); | |
const privateKey = Buffer.concat([d, x]); | |
const signature = Buffer.alloc(sodium.crypto_sign_BYTES); | |
await sodium.crypto_sign_detached( | |
signature, | |
Buffer.from(data.buffer, data.byteOffset, data.length), | |
privateKey); | |
return signature; | |
}; | |
function createJws({encodedHeader, verifyData}) { | |
const buffer = Buffer.concat([ | |
Buffer.from(encodedHeader + '.', 'utf8'), | |
Buffer.from(verifyData.buffer, verifyData.byteOffset, verifyData.length) | |
]); | |
return new Uint8Array(buffer.buffer, buffer.byteOffset, buffer.length); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment