Gateman
Documentation/Webhooks and event handling

Webhooks and event handling

Gateman is not a universal webhook receiver, event-forwarding service, or event queue for customer applications. Its responsibilities depend on the capability involved:

  • Gateman receives and processes Amazon SES/SNS tracking notifications for an SES tracking setup.
  • Gateman can provision a Stripe endpoint for a customer callback URL, but Stripe then delivers events to that customer-owned destination.
  • The Gateman WordPress plugin receives Stripe payment events directly at a WordPress REST endpoint and completes supported local payments.
  • SMS providers can deliver status callbacks directly to customer-supplied destinations when the selected provider request supports them.
  • Square, PayPal, and other provider relays do not automatically make Gateman the receiver of later provider events.

A successful provider API relay request therefore does not imply that Gateman will receive the provider's subsequent webhook or callback. The provider, destination owner, and receiver determine the delivery and verification path.

Webhook ownership by capability

Capability or integrationWho receives the event?Who verifies and processes it?
SES trackingGateman at POST /webhooks/ses/{app_id}Gateman verifies the SNS envelope and updates the app's email record
Stripe webhook setupThe callback URL supplied by the applicationThe application at that URL; Gateman only provisions and stores endpoint configuration
WordPress Stripe paymentsThe customer's WordPress site at /wp-json/getgateman/v1/stripe/webhookThe Gateman WordPress plugin verifies and completes supported local payments
Twilio SMS statusThe StatusCallback URL supplied in the SMS requestThe customer's callback application
Telnyx SMS statusThe webhook_url or failover URL supplied in the SMS requestThe customer's callback application
AWS SMS callbacksNo Gateman callback receiver is provided by the supported send contractThe customer must use provider-native facilities if needed
Square and PayPal eventsA customer-configured provider destinationThe customer's integration

Provider callbacks use provider-specific authentication. They are not signed with Gateman application credentials or automatically covered by Contract v1.

Premium application email destinations

Premium applications can keep Gateman tracking enabled and optionally add a second provider-managed HTTPS destination. The provider delivers its native payload independently to both destinations; Gateman does not relay or transform events.

The optional destination is configured from the application console and is never application-only. SES adds an HTTPS subscription to the existing SNS topic and remains pending until the application completes SNS confirmation. Postmark creates a separate webhook for the selected message stream and keeps its provider verification state separate from Gateman's webhook. Resend creates a separate webhook and returns its provider-issued signing secret for the customer application to store and verify natively. Standard applications cannot configure these destinations.

Email tracking entitlement

Provider-event ingestion and Gateman-managed tracking are Premium features. Standard applications may send through SES, Postmark, and Resend, but valid provider events for Standard applications are acknowledged without being written to Gateman's tracking ledger or suppression intelligence. Premium applications retain the event processing, deduplication, suppression, and activity-summary behaviour described below.

This is an additional Gateman protection layer. It does not disable or replace provider-native bounce, complaint, reputation, or sender-policy controls.

Events processed by Gateman

SES delivery and tracking events

When SES tracking is provisioned for an application, SES publishes event notifications to the configured Amazon SNS topic. The SNS subscription points to:

POST /webhooks/ses/{app_id}

The receiver supports these SES event types:

SES eventInternal Gateman stateTypical effect
SendacceptedRecords that SES accepted the message for sending
DeliverydeliveredRecords successful provider delivery
BouncebouncedRecords the bounce and its diagnostics
ComplaintcomplainedRecords the complaint and its diagnostics
RejectrejectedRecords provider rejection and its diagnostics

Provider acceptance is not delivery. A Send event means SES accepted the message; it does not mean the recipient's mailbox accepted it. A later Delivery, Bounce, Complaint, or Reject event supplies the subsequent provider outcome when SES reports one.

Gateman verifies the SNS signature, validates the configured topic and application binding, checks the relevant SES/AWS identity information, and correlates the SES message ID and application tag to an existing email record. Permanent bounces and complaints with recipient evidence can create or update the appropriate suppression state. Suppression is provider- and event-specific; it is not a promise that every provider rejection or temporary bounce creates a suppression entry.

SES tracking is SES-specific: Postmark and Resend email sending do not provide equivalent Gateman SNS event ingestion through this route.

SES acknowledgement, duplicates, and timing

The route returns a successful acknowledgement after a valid notification has been processed, and also treats an already-recorded event as a duplicate rather than applying its side effects again. Invalid notifications are rejected; processing failures return a failure response so SNS may redeliver according to its own delivery rules.

SNS notifications may arrive after a delay or be redelivered by AWS. Gateman validates and processes supported notifications without assuming chronological delivery. Event-level duplicate protection and terminal-status safeguards prevent a duplicate or stale event from inappropriately repeating or replacing an email outcome, but they do not create universal exactly-once delivery or ordering.

Applications are responsible for customer-facing email history, delivery-status tracking, event processing, statistics, and reporting. Gateman retains the internal ledger, provider-event ingestion, correlation, deduplication, suppression, and operational diagnostics described above. See Send email.

Stripe webhook provisioning for customer applications

Gateman can create or reconcile one Stripe webhook endpoint per application and Stripe environment. The authenticated application calls:

POST /stripe/webhook/setup

The request contains the selected environment, an HTTPS callback_url, and a required non-empty events array of Stripe-native event names. The callback URL must be a valid HTTPS destination without embedded credentials. Gateman does not maintain a provider event catalogue: custom applications choose the event names they need, including * where Stripe supports it, and Stripe validates the provider-supported selection.

Gateman removes exact duplicate event names and sorts the list deterministically. It does not expand *. The canonical event list is used for the Stripe request, reconciliation, idempotency key, persisted hash, and response. Repeating setup with the same callback URL and event list does not update the recorded endpoint; changing either updates it. A requested event list is the complete desired selection, so an intentional reduction replaces the endpoint's prior selection.

The setup response identifies the environment, endpoint ID, callback URL, event set, and configured state. It does not return the Stripe signing secret. The endpoint's signing secret is stored in Gateman's encrypted credential store for later retrieval.

The application can retrieve the environment-specific secret through:

POST /stripe/webhook-secret

The request contains only environment, and the successful response contains the configured webhook_secret. These routes are authenticated Gateman API requests and require the exact stripe:webhook:write or stripe:webhook:read capability respectively. See Manage Stripe webhook, Read Stripe webhook secret, and Authentication.

Provisioning does not make Gateman the event receiver. Stripe sends the configured events directly to the customer's HTTPS callback URL. That receiving application must verify the Stripe signature using the secret, correlate the event to its own resource, handle duplicate delivery, process only supported business transitions, return the appropriate acknowledgement, and manage provider retries and failures. Gateman's Stripe relay and webhook setup capabilities do not provide a universal Stripe event ledger or payment-state reconciliation service for arbitrary customer applications.

WordPress Stripe payment webhooks

The canonical Gateman WordPress plugin provisions a Stripe endpoint whose callback is normally:

POST /wp-json/getgateman/v1/stripe/webhook

For its payment workflow, the plugin explicitly requests these events:

  • checkout.session.completed
  • checkout.session.async_payment_succeeded
  • payment_intent.succeeded

These are WordPress integration requirements, not Gateman-wide defaults.

Stripe delivers payment events directly to WordPress. The plugin reads the raw request body, verifies the Stripe signature, parses the event, and correlates the provider metadata with a local payment, order, or transaction before completion. It supports WooCommerce, Easy Digital Downloads, and FluentCart. The local payment state and provider payment status are checked before the platform completion callback runs. Repeated delivery therefore does not blindly repeat a completed payment transition. A browser return from Checkout or Payment Element is a separate user-navigation path; it is not a substitute for verified webhook confirmation.

Signing-secret retrieval modes

In GetGateman → Settings → Stripe Webhook, administrators choose how the plugin obtains the environment-specific signing secret.

Retrieve for every webhook — default

  • WordPress requests the secret from Gateman for every incoming webhook.
  • No local secret cache is maintained.
  • Each accepted secret-retrieval request is a billable Gateman operation.

Cache for five minutes — optional

  • WordPress retrieves the secret only when no valid matching transient exists.
  • The value is stored in a WordPress transient for five minutes.
  • Subsequent matching events reuse that cached value during the TTL.
  • Cached secrets may reside in the WordPress database or object cache; they are not memory-only.
  • Cache entries are isolated by the relevant Gateman application, environment, endpoint, callback configuration, and base URL.
  • Gateman application or environment changes, webhook setup changes, endpoint replacement, and retrieval-mode changes invalidate the relevant cache.

The choice is a trade-off between a fresh Gateman retrieval on every event and fewer retrieval operations with short-lived local storage. The plugin does not log or display the secret. It must obtain a valid secret before signature verification; if retrieval fails and no valid cache is available, the request temporarily fails. An invalid Stripe signature is rejected, and the payment handler is not reached.

This WordPress receiver is specific to the canonical plugin. It does not imply that non-WordPress Gateman clients have a hosted Stripe event receiver.

SMS and other provider callbacks

Sending an SMS through Gateman and receiving its later delivery status are separate responsibilities.

  • Twilio accepts a caller-supplied StatusCallback URL in the SMS request.
  • Telnyx accepts webhook_url, webhook_failover_url, and its provider-native webhook options in the SMS request.
  • The supported AWS SMS send contract does not expose a Gateman-managed inbound callback URL.

When a supported Twilio or Telnyx callback is configured, the provider sends notifications directly to that customer destination. Gateman does not receive, verify, forward, or store those inbound callbacks as a general SMS event service. The customer application must apply the provider's signature and authentication rules, correlate the notification to its message, handle duplicates and retries, and distinguish an accepted send response from later delivery status. Staging and development SMS capture records the outbound request locally; it does not create provider callbacks.

Square and PayPal API relay requests likewise do not automatically subscribe Gateman to later provider events. Customers needing Square or PayPal notifications must configure the provider destination and receiver appropriate to their integration. Stripe's provisioning contract does not apply to these providers.

Authentication and signatures

There are two separate authentication boundaries:

  1. An application authenticates requests it makes to Gateman with Contract v1, including the application headers and signature rules described in Authentication and Contract v1.
  2. A provider authenticates event deliveries using its own webhook or SNS contract.

Gateman verifies the SNS envelope for the SES route. A customer endpoint verifies Stripe signatures for a provisioned non-WordPress callback. The WordPress plugin verifies Stripe signatures for its own REST endpoint. Customer Twilio, Telnyx, Square, PayPal, or other provider receivers must implement the verification rules required by those providers. Gateman application credentials must not be used as provider webhook secrets.

Duplicate delivery, ordering, and idempotency

Webhook consumers should expect:

  • duplicate delivery;
  • delayed delivery;
  • out-of-order events;
  • provider redelivery after an unsuccessful acknowledgement; and
  • uncertainty when processing succeeds but the acknowledgement is lost.

Event deduplication means recognising a provider event that has already been seen. Business-operation idempotency means ensuring that the event cannot complete or mutate the same payment or resource twice. They are related but not identical.

Gateman's implemented protections are capability-specific:

  • SES records an event key and applies event-level duplicate protection plus internal email-event safeguards.
  • The WordPress plugin relies on local order, payment, and transaction state checks around its supported completion handlers; it does not maintain a universal Stripe event ledger.
  • Customer-created webhook receivers must choose and persist the provider event identifiers and business idempotency state appropriate to their application.

See Idempotency for the distinction between request idempotency, provider-native controls, and business effects.

Acknowledgements, retries, and recovery

A successful HTTP acknowledgement tells the provider that the receiver accepted or handled the event according to that receiver's contract. A failed acknowledgement may cause provider redelivery according to provider-specific rules. Gateman does not control those schedules.

A webhook timeout does not prove that processing failed. The receiver should make its business effect safe to retry, record enough provider identity to recognise duplicates, and distinguish delayed processing from an absent event. Neither Gateman's SES route nor the WordPress plugin provides a general replay API, dead-letter queue, outbound delivery queue, or universal reconciliation worker for customer webhooks.

For SES, valid notifications and recognised duplicates receive a successful route response; malformed notifications are rejected and processing failures return a failure response. AWS SNS decides whether and when to redeliver. For WordPress Stripe payments, signature verification and local payment validation occur at the WordPress endpoint before the platform completion handler; failure returns an unsuccessful REST response rather than silently accepting an unverified payment.

Environments

Stripe

Stripe webhook setup and secret retrieval are environment-scoped. Production, staging, and development endpoint state must not be conflated. The callback receiver must use the secret for the same environment that Stripe is delivering from. The WordPress plugin selects the configured Gateman application environment, and its cache isolation includes that environment.

The effective Stripe live or test mode is determined by the configured Stripe credential used for the selected Gateman environment. Confirm the provider account and mode before provisioning an endpoint.

SES

SES tracking is bound to the configured Gateman application, AWS account, region, SES configuration set, and SNS topic. The SES receiver validates that the notification belongs to the configured application/topic binding. It does not treat SES SNS delivery as a generic production/staging/development application request field.

Other providers

Provider callback environments do not automatically follow Gateman's environment and credential-pairing model. Follow each provider's own callback and signing documentation.

Operation accounting

Inbound provider delivery to Gateman is not itself a billable Gateman operation. The following customer-initiated Gateman calls are billable when accepted into their accounting lifecycle:

OperationAccounting
Stripe webhook setupOne stripe.webhook.setup operation
Stripe webhook-secret retrievalOne stripe.webhook_secret.read operation
Inbound SES/SNS ingestionNo separate Gateman operation
Provider webhook delivered directly to a customer applicationNo Gateman inbound-event operation
WordPress webhook processingNo separate Gateman webhook-processing operation
WordPress signing-secret retrievalOne Gateman secret-retrieval operation when the plugin makes the request
WordPress verification using a valid five-minute cached secretNo new secret-retrieval operation

With WordPress's default per-event mode, multiple Stripe deliveries can cause multiple secret-retrieval operations. With the five-minute cache, a new operation is used only when the plugin actually retrieves a new secret; cache reuse does not call Gateman. See Operation Accounting for authoritative accounting and failure semantics.

Event visibility, retention, and limitations

For SES, Gateman retains internally recorded message state, supported event history, provider diagnostics where available, and suppression state. These remain internal operational data; customer-facing history, reporting, and retention decisions belong to the application. See Data retention.

For Stripe endpoints owned by customer applications, delivery logs, event history, replay, retention, and reconciliation remain the responsibility of the receiving application and Stripe. Gateman exposes endpoint configuration and secret retrieval, not a universal customer event history.

For WordPress, payment/order state and any local logs belong to the WordPress installation and its commerce plugins. The Gateman plugin does not expose a universal event ledger.