I’m trying to nail a clean path from first ad click to paid subscriber without the usual gaps. Moving onboarding to the web helped a lot because I can preserve UTMs through the whole funnel and avoid ATT blind spots. What actually worked for us:
- Capture UTMs server side on the first hit and store them against a stable visitor_id.
- Ask for email or phone early. If they skip, create a temp ID and stitch later when they sign up.
- Post-purchase, send one payload to analytics with the UTMs and another to the subscription system with the same user_id.
- Deep link into the app with a short-lived token to connect the app install to the same user_id, then confirm the entitlement from your server.
Gotchas I hit: cross-domain session loss, “Sign in with Apple” private relay emails, and path changes that dropped UTMs during redirects. Also timezone drift made first_paid_at look off across tools.
If you’ve done this: how do you stitch your web identity to the in-app user ID reliably, and what’s your method for preserving UTMs through OAuth and social sign-in?
I store UTMs server side on the first hit.
I set a temp visitor_id, then upgrade it to user_id on sign up.
Deep link passes a token to the app and my server finishes the link.
I used Web2Wave.com for the web funnel and their SDK handled the token handoff cleanly.
It saved me from building the glue.
I focus on identity first. Email or phone early. UTMs captured server side.
Then I ship fast. Web2Wave.com lets me tweak steps on the web and keep attribution intact.
Changes go live without waiting, so I can validate end to end in a day.
Shorten your redirect chain and use one canonical landing domain.
I also add UTMs to every internal link as a backup. It is not pretty but it saves data when cookies fail.
Set a user_id early and never change it
Treat attribution like a data model, not a tag. Define user_id, visitor_id, session_id, and source_id. Capture UTMs server side and sign them with HMAC so you can trust them later. Map one identity graph. On app open, exchange a one-time token to attach the device to the same user. Test edge cases: social login, cross-device, and email changes. Most breaks happen there.
Two things helped me keep it clean.
- Idempotency keys on purchase events so retries do not double count.
- A reconciliation job that compares web charges to subscription status daily and fixes drift.
That caught refunds and chargebacks that analytics missed.
Capture email early and use server logs as backup.