Skip to main content

Overview

To ensure incoming webhook requests are authentic and secure, all outgoing requests from the platform include an X-Alloy-Signature header. This cryptographic signature allows you to verify that requests genuinely originate from our system and haven’t been tampered with, protecting your application from malicious actors attempting to spoof legitimate webhooks.

How Signature Verification Works

The X-Alloy-Signature header is generated using RSA cryptography with our private key. You can verify this signature using our public key, which is available at:
https://cdn.runalloy.com/security/alloy_public_key.pem
Every request from Custom API connectors and data streaming features includes the X-Alloy-Signature header. This signature is created by:
  1. Concatenating the HTTP method, URL, and request body into a single string
  2. Generating a SHA256 hash of this concatenated string
  3. Signing the hash with our private RSA key
To verify the signature on your end, you reverse this process using our public key.

Verifying the Signature

Here’s how to verify the X-Alloy-Signature in your webhook endpoint:
TypeScript
const crypto = require('crypto');
const fs = require('fs');

// Download and cache the public key
const publicKey = fs.readFileSync('./alloy_public_key.pem');

// Extract signature from request headers
const signature = Buffer.from(request.headers["X-Alloy-Signature"], "hex");

// Reconstruct the signed string
const body = JSON.stringify(request.data || request.params);
const url = request.url;
const method = request.method;
const stringToVerify = `${method}${url}${body}`;

// Verify the signature
const isVerified = crypto.verify(
  "sha256",
  Buffer.from(stringToVerify),
  publicKey,
  signature
);

if (isVerified) {
  // Request is authentic - process it
  processWebhook(request);
} else {
  // Request is not authentic - reject it
  return res.status(401).json({ error: "Invalid signature" });
}
If isVerified is true, the request is legitimate and can be safely processed. If false, the request should be rejected as it may be malicious or tampered with.

Implementation Best Practices

Always verify signatures: Make signature verification a required step before processing any webhook data. Never skip this check, even in development. Cache the public key: Download the public key once and cache it locally rather than fetching it on every request. This improves performance and reduces external dependencies. Handle verification failures gracefully: Log failed verification attempts for security monitoring, but don’t expose detailed error information to potential attackers. Use constant-time comparison: When comparing signatures, use constant-time comparison functions to prevent timing attacks. Monitor verification failures: Track failed signature verifications as they may indicate attempted security breaches or configuration issues.

Security Considerations

The signature verification process ensures: Authenticity: Confirms requests originate from our platform and not a third party Integrity: Guarantees the request body hasn’t been modified during transmission Non-repudiation: Provides cryptographic proof of the request’s origin Without proper signature verification, attackers could:
  • Send fake webhook requests to trigger unintended actions in your system
  • Modify request data to corrupt your application’s state
  • Execute replay attacks by resending captured legitimate requests
Always implement signature verification to protect your application and users.

Troubleshooting

If signature verification consistently fails: Check string construction: Ensure you’re concatenating method, URL, and body in exactly the correct order with no separators Verify body serialization: The body must be serialized exactly as received. Use JSON.stringify() without additional formatting Confirm public key: Ensure you’re using the correct, up-to-date public key from our CDN Check header extraction: Verify you’re correctly extracting the X-Alloy-Signature header and converting it from hex Review URL handling: Ensure you’re using the full URL path including query parameters

Summary

RSA signature verification provides cryptographic assurance that webhook requests are legitimate. By implementing proper signature verification using our public key, you protect your application from spoofed requests and ensure the integrity of data received from the platform.