In Apex, how do I implement the webhook verification from Ironclad described here?
Their example uses Node.js and basically boils down to this:
const isValid = crypto
.createVerify(signAlgorithm)
// The data to be verified is a concatenation of eventId, nonce, and the request body
.update(eventId)
.update(JSON.stringify(body))
.update(nonce)
.verify(publicKey, signature, encoding);
return isValid;
Here is what I'm running in anonymous apex attempting to replicate the above:
String publicKey = //'-----BEGIN PUBLIC KEY-----' + // encoded in PEM format
'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx' +
'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx' +
'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx' +
'xxxxxxxxxxxxxxxxxxxxxxxx'; // + '-----END PUBLIC KEY-----';
String eventId = 'webhookEventxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
String encoding = 'base64';
String signAlgorithm = 'RSA-SHA256'; // Ironclad returns sha256
String nonce = 'xxxxxxxxxxxxxxxx';
String signature = 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx=';
String body = '{' +
'"companyID": "605b9829cdd37d296123f4b4",' +
'"payload": {' +
'"event": "workflow_launched",' +
'"templateID": "6063ac9e01a5542dafa3722b",' +
'"workflowID": "611fbd699f4a33b41d9f8295"' +
'},' +
'"webhookID": "611fb96cb670f852d58db210"' +
'}';
Boolean verified = Crypto.verify(
signAlgorithm,
Blob.valueOf(eventId + nonce + body),
Blob.valueOf(signature),
EncodingUtil.base64Decode(publicKey)
);
System.assert(verified);
I recognize that there are multiple areas where this test sample could be failing, including the formatting of the JSON body. But is the set up of the Crypto.verify()
method correct?
publicKey
string.