> ## Documentation Index
> Fetch the complete documentation index at: https://www.dynamic.xyz/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# Verifying webhook message signatures

This guide will teach you how to verify the webhook message signatures sent in the header of webhook message requests. This enables you to verify that the message originated from dynamic and the message payload has not been tampered with since only Dynamic and you have access to the secret used to sign messages.

Below is a simple typescript function that takes in the webhook secret, signature, and payload; and returns a boolean value indicating if the signature is valid or not.

```typescript theme={"system"}
import * as crypto from "crypto";

export const verifySignature = ({
  secret,
  signature,
  payload,
}: {
  secret: string;
  signature: string;
  payload: any;
}) => {
  const payloadSignature = crypto
    .createHmac("sha256", secret)
    .update(JSON.stringify(payload))
    .digest("hex");
  const trusted = Buffer.from(`sha256=${payloadSignature}`, "ascii");
  const untrusted = Buffer.from(signature, "ascii");
  return crypto.timingSafeEqual(trusted, untrusted);
};
```

The following is a practical example of how to use the verifySignature function to verify a webhook message signature for a given payload.

<Note>
  The structure of the payload object matters; if the payload object is not structured in the manner in which the message was sent the signature verification will fail.
</Note>

```typescript theme={"system"}
// webhook secret, unique per webhook
const secret = 'dyn_5LqRXtZsXit7Cjt9KktC8EGywoSkGSbGqtTud[S7AYd{LUTMcS38QRMT';

// signature sent in the header (x-dynamic-signature) of the webhook message
const signature = 'sha256=9c1eade367c30f371990918b8d79ecdd86ea2c8042849a1c22c94ad50b7d98fe';

// message payload sent in the body of the webhook POST request
const payload = {
messageId: 'd487290b-9bbd-4b50-a5f5-6620634c8dd9',
eventId: 'bfb51cec-345f-4539-b004-e3415223b86b',
eventName: 'user.deleted',
timestamp: '2024-05-31T17:21:14.890Z',
webhookId: 'c51e4b22-193e-4989-9ce2-90851d57d861',
userId: '001a4205-3d67-4956-a132-5ef41a06c78e',
environmentId: 'ba1f6471-626b-45a1-ab63-c6bf4793a1c5',
environmentName: 'sandbox',
redelivery: true,
data: {
onboardingCompletedAt: '2024-01-22T20:38:29.049Z',
metadata: {},
createdAt: '2024-01-22T20:38:27.181Z',
projectEnvironmentId: 'ba1f6471-626b-45a1-ab63-c6bf4793a1c5',
id: '001a4205-3d67-4956-a132-5ef41a06c78e',
firstVisit: '2024-01-22T20:38:27.169Z',
email: 'dynamicuser@gmail.com',
updatedAt: '2024-05-31T17:21:14.870Z',
lastVisit: '2024-01-22T20:55:10.126Z',
deletedAt: '2024-05-31T17:21:14.867Z',
},
};

const isValid = verifySignature({ secret, signature, payload });
console.log('isValid', isValid);

```

```
```
