Webhook Management - Feature Documentation
How EasyDMARC webhooks work and how to configure, secure, test, and manage them.
1. Introduction
Webhooks allow your applications to receive real-time notifications from EasyDMARC when specific events occur. Instead of continuously polling the API for updates, webhooks push data to your specified endpoint as soon as an event happens.
With EasyDMARC webhooks, you can:
- Receive instant alerts when DNS records change (SPF, MX)
- Get notified when DMARC validation fails
- Monitor non-compliance volume thresholds
- Integrate EasyDMARC events into your existing workflows, monitoring systems, or dashboards
Each webhook delivery is a standard HTTP POST request to your chosen URL, carrying a JSON payload with the event details.
2. Getting Started
Prerequisites
- An active EasyDMARC account with access to the Account Console
- An endpoint URL that can receive HTTP POST requests (must be publicly accessible or reachable from the internet)
- The endpoint must respond with a
2xxstatus code within 10 seconds
Navigating to Webhooks
- Log in to your EasyDMARC Account Console.
- Navigate to the Webhooks section from the left-side menu.
- You will see the Webhooks management page listing your existing webhooks (if any) and the signing key section at the top.
3. Creating a Webhook
To create a new webhook, click the "Create Webhook" button on the Webhooks page. A side drawer will open with the configuration form.
Configuration Fields
| Field | Required | Description |
|---|---|---|
| Name | Yes | A descriptive name for the webhook (e.g., "Production Alerts") |
| Endpoint URL | Yes | The URL where webhook payloads will be delivered |
| Events | Yes | One or more event types to subscribe to |
| Custom Headers | No | Optional key-value pairs to include in webhook requests (max 3 from UI) |
URL Validation Rules
The endpoint URL must meet the following criteria:
- Must begin with
http://orhttps:// - Supports standard domain names (e.g.,
https://api.example.com/webhooks) - Supports IPv4 addresses (e.g.,
http://192.168.1.100:8080/hook) - Supports
localhostfor development and testing - Optional port numbers and paths are allowed
- Maximum length: 1024 characters
After filling in the form and clicking "Create", the webhook will be created in an active state and immediately begin listening for the selected events.
4. Managing Webhooks
Viewing Your Webhooks
The Webhooks page displays all your webhooks in a table with the following columns:
| Column | Description |
|---|---|
| Name | The webhook's display name |
| Endpoint URL | The destination URL for event deliveries |
| Created | Date and time the webhook was created |
| Actions | Row-level action menu |
Editing a Webhook
Click the action menu (three-dot icon) on a webhook row and select "Edit". The edit drawer opens with the current configuration pre-filled. You can modify the name, endpoint URL, events, and custom headers. Click "Save" to apply changes.
Enabling / Disabling a Webhook
Each webhook has a toggle switch to control its active state:
- Enabled (Active): The webhook receives event deliveries normally.
- Disabled (Inactive): The webhook is paused. No events are delivered, but the configuration is preserved.
Toggling the state shows a confirmation dialog before the change is applied.
Deleting a Webhook
Click the action menu and select "Delete". A confirmation dialog will appear. Once confirmed, the webhook and its associated delivery history are permanently removed. This action cannot be undone.
5. Supported Event Types
When creating or editing a webhook, you select which event types trigger deliveries. The following events are currently supported:
| Event Type | Label | Description |
|---|---|---|
dns.record.changed.spf |
SPF Record Change | Triggered when a monitored domain's SPF DNS record changes. |
dns.record.changed.mx |
MX Record Change | Triggered when a monitored domain's MX DNS record changes. |
alert.validation.failed |
DMARC Record Validation Failed | Triggered when DMARC record validation fails for a domain. |
alert.noncompliance.volume |
Non-Compliant Volume Threshold | Triggered when the volume of non-compliant emails exceeds a threshold. |
Event Payload Structure
Every webhook delivery carries a JSON payload with a consistent structure:
{
"metadata": {
"eventName": "dns.record.changed.spf",
"ownerId": "org_a1b2c3d4e5",
"webhookId": "f47ac10b-58cc-4372-a567-0e02b2c3d479"
},
"data": {
"domain": "example.com",
"recordType": "SPF",
"oldValue": "v=spf1 include:_spf.old.com -all",
"newValue": "v=spf1 include:_spf.new.com ~all",
"detectedAt": "2026-02-09T14:30:00.000Z"
}
}
| Field | Description |
|---|---|
metadata.eventName |
The event type that triggered this delivery |
metadata.ownerId |
Your organization identifier |
metadata.webhookId |
The ID of the webhook configuration that matched |
data |
Event-specific payload data (varies by event type) |
6. Custom Headers
Custom headers allow you to include additional HTTP headers in every webhook delivery. This is useful for:
- Authenticating webhook requests with your endpoint (e.g.,
Authorization: Bearer <token>) - Routing requests in API gateways or load balancers
- Adding correlation or tracking identifiers
Adding Custom Headers
In the Create or Edit webhook drawer, expand the Custom Headers section. Click "Add Header" to add a new key-value pair. Fill in both the header name and value fields.
Constraints
| Constraint | Value |
|---|---|
| Maximum headers (via UI) | 3 |
| Maximum headers (via API) | 10 |
| Header name max length | 128 characters |
| Header value max length | 1024 characters |
| Header name format | Letters, numbers, hyphens, underscores only ([a-zA-Z0-9\-_]) |
Reserved Headers
The following header names are reserved by the system and cannot be used as custom headers:
| Reserved Header | Reason |
|---|---|
content-type |
Set automatically to application/json |
x-webhook-secret |
Used for webhook signature verification |
x-webhook-event |
Contains the event type name |
x-webhook-delivery |
Contains the unique delivery ID |
user-agent |
Set to EasyDMARC-Webhook-Service |
host |
Determined by the endpoint URL |
connection |
Managed by the HTTP client |
content-length |
Calculated automatically from the payload |
Content-Type, content-type, and CONTENT-TYPE are all considered reserved.7. Testing Webhooks
Before relying on a webhook in production, you can verify that your endpoint receives and processes payloads correctly using the Test Webhook feature.
How to Test
- Click the "Test Webhook" button on the Webhooks page to open the test drawer.
- Select an alert example event type from the dropdown. Available options:
- SPF Record Change
- MX Record Change
- DMARC Record Validation Failed
- Non-Compliant Volume Threshold Reached
- Enter the endpoint URL you want to test.
- Optionally, add custom headers that should be included in the test request.
- Click "Send Test" to dispatch the test payload.
Reading Test Results
After the test completes, the drawer displays:
- Status Code: The HTTP status code returned by your endpoint
- Response Body: The raw response body from your endpoint
- Success/Error Indicator: A visual indicator showing whether the test passed (2xx response) or failed
8. Webhook Signing Key & Security
Every webhook delivery can include an HMAC-based signature that allows you to verify the request genuinely originated from EasyDMARC.
What Is the Signing Key?
Your organization has a unique signing key (a 32-byte hex string) that is shared across all your webhooks. This key is used to compute an HMAC-SHA256 signature of the payload, which is sent in the X-Webhook-Secret header.
Finding Your Signing Key
The signing key is displayed at the top of the Webhooks page. By default, it is partially masked (showing only the last 5 characters). Use the following controls:
- Show/Hide (eye icon): Toggle between the masked and full key view
- Copy: Copy the full signing key to your clipboard
- Regenerate: Generate a new signing key (see below)
Regenerating the Signing Key
Click the "Regenerate" button and confirm the action in the dialog. The old key is invalidated immediately, and a new key is generated. There is a cooldown period between regenerations.
Verifying Webhook Signatures
When your endpoint receives a webhook, extract the signature from the X-Webhook-Secret header and compare it against a locally computed HMAC-SHA256 hash of the request body.
Node.js Example
const crypto = require('crypto');
function verifyWebhookSignature(payload, signature, secret) {
const payloadString = typeof payload === 'string'
? payload
: JSON.stringify(payload);
const expectedSignature = crypto
.createHmac('sha256', secret)
.update(payloadString)
.digest('hex');
return expectedSignature === signature;
}
// Usage in an Express route handler
app.post('/webhook', (req, res) => {
const signature = req.headers['x-webhook-secret'];
const isValid = verifyWebhookSignature(req.body, signature, YOUR_SIGNING_KEY);
if (!isValid) {
return res.status(401).json({ error: 'Invalid signature' });
}
// Process the webhook event
console.log('Event received:', req.body.metadata.eventName);
res.status(200).json({ received: true });
});
Python Example
import hmac
import hashlib
import json
def verify_webhook_signature(payload, signature, secret):
if isinstance(payload, dict):
payload = json.dumps(payload, separators=(',', ':'))
expected = hmac.new(
secret.encode('utf-8'),
payload.encode('utf-8'),
hashlib.sha256
).hexdigest()
return hmac.compare_digest(expected, signature)
9. Webhook Delivery & Retry Logic
How Delivery Works
- An event is triggered in the EasyDMARC system (e.g., a DNS record change is detected).
- The system identifies all active webhooks subscribed to that event type.
- For each matching webhook, an HTTP POST request is sent to the configured endpoint URL.
HTTP Headers Included in Every Delivery
Each webhook delivery includes the following system headers:
| Header | Value | Description |
|---|---|---|
Content-Type |
application/json |
Payload is always JSON |
User-Agent |
EasyDMARC-Webhook-Service |
Identifies the sender |
X-Webhook-Event |
(event type) | The event that triggered this delivery |
X-Webhook-Delivery |
(UUID) | Unique identifier for this specific delivery attempt |
X-Webhook-Secret |
(HMAC signature) | HMAC-SHA256 signature for verification |
Any custom headers configured on the webhook are also included, but they cannot override system headers.
Success Criteria
A delivery is considered successful when your endpoint responds with any 2xx HTTP status code (200–299) within 10 seconds.
Retry Behavior
If a delivery fails (non-2xx response, timeout, or connection error), the system retries with exponential backoff:
| Attempt | Delay Before Retry | Cumulative Wait |
|---|---|---|
| 1st retry | 1 second | 1 second |
| 2nd retry | 2 seconds | 3 seconds |
| 3rd retry | 4 seconds | 7 seconds |
| 4th retry | 8 seconds | 15 seconds |
| 5th retry | 16 seconds | 31 seconds |
The formula is: delay = 1000ms × 2^(attempt - 1)
After 5 failed retry attempts, the delivery is marked as failed.
Delivery Statuses
| Status | Description |
|---|---|
| Pending | Delivery is queued or in the process of being retried |
| Success | Endpoint responded with a 2xx status code |
| Failed | All retry attempts have been exhausted without a successful response |
10. Troubleshooting & FAQ
My webhook isn't receiving events
- Verify the webhook is in Active state (not disabled).
- Confirm the endpoint URL is publicly accessible from the internet.
- Check that the webhook is subscribed to the correct event types.
- Ensure your endpoint responds with a
2xxstatus code within 10 seconds. - Check your server/firewall logs for blocked incoming requests from the
EasyDMARC-Webhook-Serviceuser agent.
URL validation fails when creating a webhook
- The URL must begin with
http://orhttps://. - The URL must be a valid domain name, IPv4 address, or
localhost. - Special characters in paths must be properly encoded.
- The URL cannot exceed 1024 characters.
Reached webhook limit (maximum 5)
- Review your existing webhooks and delete any that are no longer needed.
- Consider consolidating webhooks by subscribing a single webhook to multiple event types.
- Contact your account manager if you need a higher limit for your organization.
Test webhook returns an error
- Check that the test URL is accessible and accepting POST requests.
- Verify the endpoint is not behind authentication that blocks the request.
- Review the status code and response body shown in the test results for details.
- Ensure the endpoint responds within the timeout window (10 seconds).
- If using custom headers, verify they do not conflict with reserved headers.
Webhook deliveries keep failing
- After 5 retry attempts, deliveries are marked as failed. Check your endpoint health.
- Ensure your endpoint can handle the request volume without timing out.
- Verify there are no network-level blocks (IP allowlists, WAF rules) preventing delivery.
- Check that your TLS/SSL certificate is valid if using HTTPS.