info@cetonix.com +91 (966) 512-1196 Mon–Fri, 09:30–18:00 IST
HomeInsightsWebhooks: Signature Verification, Replay and SSRF

Webhooks: Signature Verification, Replay and SSRF

Webhooks are an inbound API you did not design and an outbound request you did not intend. Both directions produce findings.

Security Testing Cetonix
Webhooks: Signature Verification, Replay and SSRF

Webhooks are two security problems wearing one name. Receiving them means accepting requests from the internet that trigger business logic. Sending them means making HTTP requests to a URL somebody else supplied. Both directions produce findings, and assessments frequently cover only one.

Receiving: the inbound problem

Signature verification, or the absence of it

The provider signs the payload; you verify the signature. The failure modes, in the order we find them:

  • No verification at all. The endpoint accepts any request. Anyone who learns the URL can trigger whatever the handler does — mark an invoice paid, provision an account, change a subscription tier.
  • Signature computed but not compared. The code calculates the expected value and never checks it against the header, or checks it in a branch that cannot be reached.
  • Non-constant-time comparison. Using == rather than a constant-time function. Practically difficult to exploit over a network, still worth fixing, and a reliable indicator of how the rest of the handler was written.
  • Verifying a re-serialised body. The signature covers the exact bytes received. Parsing the JSON and re-serialising before verification breaks on whitespace and key ordering, and teams sometimes “fix” this by disabling verification.

Replay

A valid signed request stays valid forever unless something prevents reuse. Capture one legitimate “payment succeeded” webhook and send it repeatedly.

The defences are a timestamp inside the signed payload with a tolerance window, and idempotency — recording the event ID and ignoring duplicates. Idempotency is the stronger control and it also fixes the duplicate-delivery problem every webhook provider warns you about, which is a good argument for implementing it on reliability grounds alone.

Trusting the payload

Even with a verified signature, the payload states what the provider believes. Where the value matters — an amount, a status, an entitlement — the robust pattern is to treat the webhook as a notification that something changed, then call the provider’s API to read the authoritative state. Slower, and materially harder to abuse.

Sending: the outbound problem

If your product lets customers register a webhook URL, you have given them a server-side request forgery primitive, and it will be tested.

  • Cloud metadata endpoints169.254.169.254 and equivalents. Where IMDSv1 is still enabled, this is a direct route to instance credentials.
  • Internal services reachable from your application network and not from the internet.
  • Redirect chains. An allowed external URL that returns a 302 to an internal one. Validating only the initial URL is a common gap.
  • DNS rebinding. A hostname that resolves to a public address at validation time and an internal one at request time. Defeats naive allowlisting, and the fix is to resolve once and connect to the resolved address.
  • Protocol smuggling through file://, gopher:// and similar, where the HTTP client follows them.

The defence that holds is egress control: deliver webhooks from an isolated component with no route to internal networks or metadata services. Allowlists and blocklists at the application layer are worth having and are not sufficient on their own.

What to hand a tester

For webhook testing we need the provider’s signing documentation, a sample signed payload, the endpoint list, and — for outbound webhooks — the ability to register a URL we control. Without the last one, the SSRF surface can only be reasoned about rather than demonstrated.

← The ISO/IEC 27001:2013 Transition Deadline Is Close. Where That Leaves YouBusiness Logic Flaws: The Vulnerability Class No Scanner Reports →