Use the SDK built-in WebhookHandler
We strongly recommend using the SDK methodwebhook().handleWebhook(), which automatically handles:
- Signature verification
- JSON parsing and event routing
- Response body construction
Idempotent handling
Waffo may deliver the same event multiple times. Make sure your handling logic is idempotent:Handle final state, not delivery order
Webhooks are delivered asynchronously, so the order in which your endpoint receives related callbacks is not guaranteed. In subscription first-period scenarios, bothSUBSCRIPTION_STATUS_NOTIFICATION and SUBSCRIPTION_PERIOD_CHANGED_NOTIFICATION may be sent. Do not depend on the arrival order of these two callbacks.
- Do not update final business state based only on callback arrival order
- Choose an idempotency key for the event’s granularity, such as the event ID or your business order ID; combine
subscriptionIdand the period for period entitlements so that later periods are not skipped - If you subscribe to both
SUBSCRIPTION_STATUS_NOTIFICATIONandSUBSCRIPTION_PERIOD_CHANGED_NOTIFICATION, callPOST /api/v1/subscription/inquiryafter receiving either callback, then run one unified subscription callback flow based on the final inquiry result
Grant Subscription entitlements
UseSUBSCRIPTION_PERIOD_CHANGED_NOTIFICATION to trigger checks before granting period entitlements. Verify the signature, then check the final payment result for the relevant period. Receiving a notification does not by itself mean the payment succeeded.
- Check that the Subscription, period, and amount match the relevant plan and the amount due for that period
- Grant the corresponding entitlements only after the period’s payment succeeds and the checks pass
- Record entitlement grants by Subscription and period so that duplicate notifications do not grant them again
- When handling
PAYMENT_NOTIFICATION, first useresult.subscriptionInfo.subscriptionEventto distinguish period charges, payment method additions, and top-ups. Do not use the latter two as the basis for granting a new period’s entitlements; see Subscription payment events
Fast responses
- The SDK automatically builds the response after the handler finishes executing
- Time-consuming operations (such as sending emails or updating external systems) should be handled asynchronously
- If an exception is thrown in the handler, the SDK automatically returns a failure response
Security
- Always verify
X-SIGNATURE(handled automatically by the SDK) - Use an HTTPS endpoint
- Verify the signature before processing the event—do not execute any business logic before verification passes