Signature Verification

Ensure the payloads you receive are sent by ZWITCH.

When dealing with financial transactions, it is important to verify that your transactions were processed by us. This helps prevent fraud, keeping both you and your customers happy.

We include a signature that you can use to verify that the webhook payload you receive is legitimate and sent by us. The signature is sent against the x-zwitch-signature parameter in the header in all webhooks.

Verify Signature

Follow the below steps to verify the webhook signature.

  1. Log into your ZWITCH Dashboard.
  2. Select the mode in which you want to verify the signature.
  3. Navigate to DevelopersWebhooks.
  4. Reveal and copy your Signing Secret.
  5. Remove all new lines and whitespaces from the payload you want to verify.
  6. Generate a SHA256 signature using your Signing Secret from step 4 and the payload from step 5.
  7. Compare the signature you generated with the one sent against the x-zwitch-signature parameter in the webhook header. If they match, the payload is genuine.

Sample Code

You can use the below code to generate a signature on your server.

import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
import java.nio.charset.StandardCharsets;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import org.apache.commons.codec.binary.Hex;

public class SignatureGenerator {

    public static String generateSignature(String signingSecret, String responseBody) {
        try {
            byte[] secretKeyBytes = signingSecret.getBytes(StandardCharsets.UTF_8);
            SecretKeySpec keySpec = new SecretKeySpec(secretKeyBytes, "HmacSHA256");

            Mac mac = Mac.getInstance("HmacSHA256");
            mac.init(keySpec);

            byte[] prehash = responseBody.getBytes(StandardCharsets.UTF_8);
            byte[] hash = mac.doFinal(prehash);

            return Hex.encodeHexString(hash);
        } catch (NoSuchAlgorithmException | InvalidKeyException e) {
            e.printStackTrace();
            return null;
        }
    }

    public static void main(String[] args) {
        String signingSecret = "<enter_your_signing_secret>";
        String responseBody = "<enter your webhook payload without the headers>";//raw webhook request body and also use escape JSON

        String requestSignature = generateSignature(signingSecret, responseBody);
        System.out.println(requestSignature);
    }
}
const crypto = require('crypto');

const signingSecret = '<enter_your_signing_secret>';
const responseBody = '<enter your webhook payload without the headers>';//raw webhook request body

const prehash = JSON.stringify(JSON.parse(responseBody));
const requestSignature = crypto.createHmac('sha256', signingSecret).update(prehash).digest('hex');

console.log(requestSignature);

import hashlib
import hmac
import base64

secret_key = b'<enter_your_signing_secret>'  
response_body = b'<enter your webhook payload without the headers>'//raw webhook request body

request_signature = hmac.new(secret_key, response_body, hashlib.sha256)
signature_hexdigest = request_signature.hexdigest()

print(signature_hexdigest)
require 'openssl'
require 'json'

def generate_signature(signing_secret, response_body)
  prehash = JSON.parse(response_body).to_json
  digest = OpenSSL::Digest.new('sha256')
  hmac = OpenSSL::HMAC.hexdigest(digest, signing_secret, prehash)
  hmac
end

signing_secret = '<enter_your_signing_secret>'
response_body = '<enter your webhook payload without the headers>'

request_signature = generate_signature(signing_secret, response_body)
puts request_signature
<?php

$signing_secret = '<enter_your_signing_secret>'; 
$response_body = '<enter your webhook payload without the headers>';//raw webhook request body

$request_signature =  hash_hmac('sha256', $prehash, $signing_secret);

echo "$request_signature";
?>