Validating Webhooks

Learn how to validate Alloy Webhooks by generating a RSA Signature

Overview

In the previous article, we looked at which headers Alloy Unified API sends along with each webhook. Included in these headers is the x-alloy-signature. In this article, we'll look at how to generate the signature to validate authenticity of incoming Alloy Webhooks.

Generating the RSA Signature

To validate outgoing API requests are from Alloy Unified API, we’ve implemented an RSA Signature.

This signature is signed with our public key which you can validate: here. Once you've validated the authenticity of the x-alloy-signature you can confirm webhooks are indeed coming from Alloy Unified API are trusted and legitimate. Let’s take a look at how this works.

This header can be reconstructed and verified by making a SHA256 hash against the public key and a concatenated string containing the outgoing request data.

We’ve built an example validation code snippet in Node.js below. This snippet will generate a signature that should be identical to the value of X-Alloy-Signature. If this value matches X-Alloy-Signature, you should feel confident that the request is indeed coming from Alloy and is a trusted request, if the value you generated does not match the signature value in our header, then this should be considered a malicious request.

const publicKey = `https://cdn.runalloy.com/security/alloy_public_key.pem`;
const signature = Buffer.from(request.headers['X-Alloy-Signature'], 'hex');
const body = JSON.stringify(request.data || request.params);
const url = request.url;
const method = request.method;
const stringToVerify = `${method}${url}${body}`;

const isVerified = crypto.verify(
  'sha256',
  Buffer.from(stringToVerify), 
  publicKey,
  signature
);

Wrapping Up

In this article, we looked at how to generate an RSA signature and verify its authenticity.