Skip to content

Webhook Integration Guide

Webhook Integration

Our webhook integration lets you receive real-time status updates directly from our system — no need to repeatedly query the Status API. When a relevant event occurs, we’ll send an HTTP POST request to your configured endpoint containing the event data in JSON format.

What is a Webhook?

A webhook is a simple way for one system to send automated updates to another system over the web. Instead of polling our API for new information, you provide a public HTTPS endpoint — and we’ll push updates to you as they happen.

Security: HMAC Signatures

Each webhook request we send is HMAC-signed to ensure authenticity and integrity.

  • We compute an HMAC using SHA-256 over the raw request body.
  • The signature is created using a shared signing key.
  • The resulting HMAC is Base64-encoded and sent in the header: x-earlybird-hmac-sha256: <signature>

Verifying the Signature (C# Example)

You can verify the authenticity of a webhook by recomputing the HMAC using your signing key and comparing it to the signature in the header.

using System.Security.Cryptography;
using System.Text;
bool VerifyWebhook(string requestBody, string receivedSignature, string signingKey)
{
// Compute the expected Base64 HMAC-SHA256
using var hmac = new HMACSHA256(Encoding.UTF8.GetBytes(signingKey));
var hash = hmac.ComputeHash(Encoding.UTF8.GetBytes(requestBody));
var expectedSignature = Convert.ToBase64String(hash);
// Compare in constant time to prevent timing attacks
return CryptographicOperations.FixedTimeEquals(
Convert.FromBase64String(receivedSignature),
Convert.FromBase64String(expectedSignature)
);
}

If the computed signature matches the one in the x-earlybird-hmac-sha256 header, the webhook request is valid and originated from our system.

Example Webhook Request

Full example request

Terminal window
POST /webhooks/status HTTP/1.1
Host: customer.example.com
Content-Type: application/json
x-earlybird-hmac-sha256: j74NivefCjJuqc7DJV6LIgn2IxPb2iKLKsMNh+S8ZAQ=
{"status": "Created", "location": null, "eventTime": "2025-10-10T12:20:12.148Z", "trackingIds": ["00395400000000064333"], "detailedStatus": "Created", "distributionType": "EarlyBird", "displayToConsumer": false, "consumerDescription": [], "detailedStatusDescription": [{"value": "Information om leveransen har skapats.", "languageCode": "sv"}, {"value": "Information about the delivery has been created.", "languageCode": "en"}]}

Signing key used

Terminal window
12345678

Signature computation (c#)

using System.Security.Cryptography;
using System.Text;
using System;
var key = "12345678";
var body = """
{"status": "Created", "location": null, "eventTime": "2025-10-10T12:20:12.148Z", "trackingIds": ["00395400000000064333"], "detailedStatus": "Created", "distributionType": "EarlyBird", "displayToConsumer": false, "consumerDescription": [], "detailedStatusDescription": [{"value": "Information om leveransen har skapats.", "languageCode": "sv"}, {"value": "Information about the delivery has been created.", "languageCode": "en"}]}
""";
using var hmac = new HMACSHA256(Encoding.UTF8.GetBytes(key));
var hash = hmac.ComputeHash(Encoding.UTF8.GetBytes(body));
var signature = Convert.ToBase64String(hash);
Console.WriteLine(signature);

Resulting signature

Terminal window
j74NivefCjJuqc7DJV6LIgn2IxPb2iKLKsMNh+S8ZAQ=

Your system should verify the signature before processing the payload.

You can reproduce this signature (j74NivefCjJuqc7DJV6LIgn2IxPb2iKLKsMNh+S8ZAQ=) by computing the HMAC-SHA256 of the exact body above, including all whitespace and line breaks, using the key 12345678.

Managing Webhooks in the Customer Portal

You can manage your webhook endpoints in the Customer Portal:

  1. Go to “Inställningar” (“Settings”)
  2. Expand the “Webhook”-section and fill in the form. The url can not include any redirects, and must be publicly accessable.
  3. Give the webhook a name to help remember what it is used for.
  4. Provide, or generate, a shared key. This key should be kept secret and is after the webhook is generated no longer visible.
  5. Use this key to verify incoming webhook requests as described above.

You can add, disable, or remove endpoints at any time.