Beta Release
This is pre-release documentation for an API in public beta and is subject to change.
v2 Webhooks

Validate Notifications

Validate Square Webhook event notifications.

Backend
Inventory API
Node.js (SDK)

Once you are sure your webhooks are working, you will need to add code to your notification URL so that your application does something with the events it receives.

We recommend validating webhook notifications to confirm they came from Square. While not strictly required, validating the sender adds an extra layer of security and helps avoid man-in-the-middle attacks.

All webhook notifications from Square include an X-Square-Signature header. The value of this header is an HMAC-SHA1 signature generated using your webhook notification URL and the body of the request excluding all whitespace.

You can validate the webhook notification by generating the HMAC-SHA1 in your own code and comparing it to the signature of the notification you received. You will need the Signature Key assigned by the Square Application Dashboard in the Webhooks settings page for your application.

Information you will need
Permalink Get a link to this section

  • The webhook signature key assigned by the Square Developer Portal in the Webhooks settings page for your application. You will compare the webhook signature key to the key provided in the notification.

In the Webhooks page for your application, click on the Connect v2 Webhook endpoint that you are verifying. The Webhook Details dialog opens and shows the signature key of the subscription:

v2WebhookDetails

Step 1: Get the notification signature and body
Permalink Get a link to this section

// This example uses Express to handle HTTP requests
const express = require('express');
const app = express();

// Parse HTTP bodies as JSON
app.use(express.json());

app.post('/webhooks', function(req, resp) {
  // Notification signature: 'gf6sy...wOFw9Gw='
  // Note: Signature is truncated for illustration
  const signature = req.header('X-Square-Signature');

  /*
  webhook notification body
  {
    "merchant_id": "6VEKB6...",
    "type": "webhooks.test_notification",
    "event_id": "44db71b7-c20a-416e-428a-fd8e1837e4f5",
    "created_at": "2019-07-31T17:10:55.49604564Z",
    "data": {
      "type": "webhooks",
      "id": "8e4600d9-7e6c-44d5-8942-31fb7e45ef0e"
    }
  }
  */
  const body = req.body;

  // Send a 200 response to indicate success
  resp.sendStatus(200);
});

app.listen(3000, () => console.log('listening for webhooks on port 3000'));

Did you know?

You can get the timestamp of the initial event notification delivery, the number of notification retries, and the Square environment that generated the notification by reading the Event metadata headers on the event message.

Step 2: Validate the signature
Permalink Get a link to this section

The example function below generates an HMAC-SHA1 signature from your notification URL and the notification body, then compares it with the provided signature.

// The crypto module provides cryptographic functionality
const crypto = require('crypto');

function isValidSignature(body, url, signature) {
  // Concatenate your notification URL and
  // the JSON body of the webhook notification
  const combined = url + JSON.stringify(body);

  // Webhook subscription signature key defined in dev portal for app 
  // webhook listener endpoint: https://webhook.site/my-listener-endpoint
  // Note: Signature key is truncated for illustration
  const signatureKey = 'uTYf8X...0HGvYg';

  // Generate the HMAC-SHA1 signature of the string
  // signed with your webhook signature key
  const hmac = crypto.createHmac('sha1', signatureKey);
  hmac.write(combined)
  hmac.end()
  const checkHash = hmac.read().toString('base64');
    
  // Compare HMAC-SHA1 signatures.
  if (checkHash === signature) {
    console.log('Validation success!');
  } else {
    console.log('Validation error.');
  }
}