- Identify with your stable customer id before presenting offers.
Encore.identify(customerId)keys every exposure and claim to that id. - Forward each subscription event server-side to Encore’s webhook with
user.app_account_idset to that same id, byte-identical, plus the matching event verb.
app_account_id. That is the whole job:
no id plumbing through your checkout, no other client work.
Using RevenueCat?
If RevenueCat manages your subscriptions, you are most likely done already. Encore natively ingests RevenueCat webhooks, so you never build the server-side forwarding in step 2 yourself. The whole recipe is two alignment moves:- Identify with your RevenueCat app user id. Call
Encore.identify()with the same id you pass to RevenueCat asapp_user_id(equivalently, use one stable customer id for both). This is step 1 below with one extra constraint: the two ids must match. - Point RevenueCat’s webhook forwarding at Encore. Add the per-app receiver URL from your Encore dashboard’s webhook settings as a RevenueCat webhook target. See RevenueCat’s webhook guide for how to add a webhook in their dashboard. Many publishers already have this configured; if so, just confirm the URL.
Step 1: identify before you show offers
Callidentify() with your own stable customer
id, before any offer is presented:
getAppAccountId()
returns. Without identify(), the SDK falls back to an auto-generated anonymous id, and
your server has no way to reproduce that value later, so your subscription events can
never link back. On web this is critical: identify as soon as you know who the user is,
and always before show().
Step 2: forward subscription events with the same id
Whenever a subscription event happens in your billing system (subscribe, renew, cancel, and so on), your server POSTs it tohttps://api.encorekit.com/encore/webhooks/encore
with:
user.app_account_id: the same customer id from step 1, byte-identicalsubscription.original_transaction_id: your biller’s subscription idevent_type: the matching Encore verb, for exampledid_subscribeordid_renew
buildEncoreHeaders signing helper, the payload
schema, the verb list, and responses) lives in the
Webhook Ingestion reference. This guide
only composes it:
Using Another Billing Provider?
If your subscriptions run through Stripe, Paddle, or your own custom billing rather than RevenueCat, the two manual steps above are your path. Identify with your stable customer id (step 1), then forward each subscription event server-side to Encore’s webhook with that same id (step 2). That is the canonical path for any biller Encore does not ingest natively; there is no other client work.Gotchas
- Byte-identical id.
user.app_account_idmust equal theidentify()id exactly; any prefixing, casing, or trimming difference breaks the join silently. - Identify before show, not after. Exposures recorded before
identify()are keyed to the anonymous id and are not retro-linked; a late identify leaves them unattributed. - Resolve the id server-side. Read the customer id from your own auth session or subscription records, never from the client request body: a spoofed id attributes someone else’s subscription.
- Every event carries the id.
user.app_account_idis required on every event, not just the first; an event without it is acknowledged but dropped. See how the join works. - Use the canonical verbs. An unrecognized
event_typeis accepted and stored but cannot be projected into measurement; map your biller’s events to the verb list.
Related
- Webhook Ingestion reference: the full contract this guide forwards to.
identify(): the identity model, includinggetAppAccountId().- Reduce Paywall Churn: an offer flow whose outcomes this attribution measures.