PHP

Secure Webhook Signature Verification

Implement robust PHP code to verify HMAC-SHA256 signatures for incoming webhooks, ensuring data integrity and preventing spoofed requests.

<?php

function verifyWebhookSignature(string $payload, string $signatureHeader, string $secret, string $algo = 'sha256'): bool
{
    // Extract the signature from the header. Format might be 't=timestamp,v1=signature'
    // For simplicity, let's assume the signature is directly the hex hash.
    // Real-world APIs often prefix it (e.g., 'sha256=' or 'v1=')
    // Adjust this parsing based on the specific API's documentation.
    $providedSignature = str_replace(["sha256=", "v1=", "t="], "", $signatureHeader);
    $providedSignature = trim($providedSignature);

    if (empty($providedSignature)) {
        return false; // No signature provided
    }

    // Calculate the expected signature
    $expectedSignature = hash_hmac($algo, $payload, $secret);

    // Use hash_equals for timing attack safe comparison
    return hash_equals($expectedSignature, $providedSignature);
}

// Example Usage:
// $secret = 'YOUR_WEBHOOK_SECRET'; // This should be a strong, randomly generated string
// $payload = file_get_contents('php://input'); // The raw JSON payload from the request body
// $signatureHeader = $_SERVER['HTTP_X_HUB_SIGNATURE_256'] ?? ''; // e.g., for GitHub, or 'HTTP_X_STRIPE_SIGNATURE' for Stripe

// if (verifyWebhookSignature($payload, $signatureHeader, $secret)) {
//     // Signature is valid, process the webhook event
//     http_response_code(200);
//     echo 'Webhook received and verified.';
//     // file_put_contents('webhook.log', date('Y-m-d H:i:s') . ' - Valid webhook: ' . $payload . "
", FILE_APPEND);
// } else {
//     // Signature is invalid or missing, reject the request
//     http_response_code(403);
//     echo 'Invalid webhook signature.';
//     // file_put_contents('webhook_error.log', date('Y-m-d H:i:s') . ' - Invalid signature or missing: ' . $signatureHeader . ' with payload: ' . $payload . "
", FILE_APPEND);
// }

?>
How it works: This PHP snippet provides a `verifyWebhookSignature` function essential for securing webhook endpoints. It takes the raw request payload, the signature header (e.g., `X-Hub-Signature-256`), and your secret key to calculate an expected HMAC signature. By comparing this expected signature with the one provided in the header using `hash_equals` (which is resistant to timing attacks), you can confirm the webhook's authenticity and integrity, ensuring that the request truly came from the expected service and hasn't been tampered with.

Need help integrating this into your project?

Our team of expert developers can help you build your custom application from scratch.

Hire DigitalCodeLabs