Webhooks and APIIntegrations

Stripe

Receive Stripe payment events in Wexio flows

Wexio verifies Stripe signatures natively. Paste the signing secret from the Stripe dashboard and Wexio handles the Stripe-Signature header, including timestamp tolerance and multi-v1 signature rotation.

Provider docs: Setting up webhooks in Stripe

Setup

1. Create an Inbound Connection

Go to Settings → Webhooks and API → Webhooks → New connection → Inbound. Click the Stripe chip under Provider presets > Dedicated providers, or set Authentication mode to Stripe.

Copy the Wexio endpoint URL: https://api.wexio.io/webhooks/in/{connectionId}. You paste the signing secret into Signing secret after the next step.

2. Register the Endpoint in Stripe

In Stripe, go to Developers → Webhooks → Add endpoint and fill in these fields.

FieldValue
Endpoint URLThe Wexio endpoint URL
Events to sendThe events you need, for example checkout.session.completed, invoice.paid, customer.subscription.created

Stripe shows the signing secret (it starts with whsec_) after you create the endpoint. Copy it and paste it into the Wexio Signing secret field.

3. Configure Contact Resolution

Stripe payloads carry emails or customer IDs. Either works.

Identifier typeJSON pathNotes
Email$.data.object.customer_emailMatches Wexio contacts by their email field
Email$.data.object.receipt_emailAlternative for Payment Intent events

If you store stripe_customer_id on your Wexio contacts, you can also map by custom field using a flow variable lookup after the trigger fires.

4. Capture the Schema

Tap Capture schema in Wexio. In Stripe, open your endpoint, click Send test webhook and pick the event type. Wexio absorbs the sample and fills the field picker.

5. Bind a Flow

Add a Webhook Received trigger to a flow and pick this connection. To run one flow per Stripe event type, add a Condition card on webhook.type.

Example - Invoice Paid to WhatsApp Receipt

  • Stripe event: invoice.paid
  • Wexio connection: identifier Email with $.data.object.customer_email
  • Flow:
    1. Webhook Received
    2. Condition: branch on {{webhook.type}} EQUALS invoice.paid
    3. WA Template "invoice_receipt" with {{webhook.data.object.amount_paid}} and {{webhook.data.object.number}}

Timestamp Tolerance and Replays

Stripe signs each event with a timestamp. Wexio rejects anything outside ±5 minutes to prevent replay attacks.

Stripe retries events when your endpoint returns non-2xx. Stripe sets how long it retries; see its webhook docs. A replay that arrives after the tolerance window is logged as UNAUTHORIZED: Stripe signature timestamp outside ±5 min tolerance. This is expected, and Stripe stops retrying in the end. To recover missed events, fetch them with the Events API in Stripe.

Rotation

Stripe supports dual signing during rotation and shows two valid secrets for a configurable window. To rotate with zero downtime:

  1. In Stripe, click Roll signing secret on the endpoint.
  2. Copy the new secret.
  3. In Wexio, open the connection, click Change under Authentication and paste the new signing secret.

Stripe keeps signing with both secrets until the rollover window ends.

Troubleshooting

SymptomCauseFix
UNAUTHORIZED: Stripe signature mismatchWrong signing secretRe-copy it from Stripe and check you are on the right endpoint (test or live)
UNAUTHORIZED: Stripe signature timestamp outside ±5 min toleranceClock skew or an old replayCheck NTP on your clock. Very old replays are rejected
Live events in history, but the flow does not runIDENTIFIER_NOT_FOUND: no matching contact in Wexio yetCreate the contact via the People API, or add a branch that creates it on a miss
Missing eventsThe Stripe endpoint is not subscribed to that event typeEdit the endpoint in Stripe and add the event

Was this page helpful?

On this page