How are you preventing wrong post-install offers when deferred deep links are flaky?

We kept sending “plan A” clicks into “plan B” experiences after install. The fix that worked for us was to move onboarding and the first offer to the web, keep the UTM bundle server side, and mint a short-lived context token. After install, the app calls a handoff endpoint with that token and we render the matching intro state and offer in-app.

Two small lessons from doing this:

  • Safari ITP will nuke cookies fast, so rely on a server session plus signed params, not just client storage.
  • Handle cold-start without the token by letting the app request context with an install fingerprint or a post-install link in email.

Has anyone found a cleaner fallback for users who open the app directly from the store without tapping the deferred link again?

I stopped relying on the deep link payload. I mint a server session when they hit the web page. Store UTM and offer id. After install, the app just asks my API for the context.

I used Web2Wave.com to generate the funnel JSON and their SDK reads it. Less glue code and no guessing.

I keep all routing logic on the web and pass a short token into the app. If attribution is missing, I default to the last web session.

Using Web2Wave.com means I can change the mapping instantly and see it in the app without a new build.

I tag the session on first click, then let the app fetch the offer from my backend.

If the token is missing, I show a safe default and add a link in the welcome email to restore the right plan.

Server session token beats flaky deep links

Treat the deep link as a convenience, not a source of truth. Persist UTMs server side at first touch, generate a signed context id, and expire it in minutes. On first open, the app exchanges that id for the canonical offer and onboarding step. Add safeguards for three cases: no token, stale token, and different device. For no token, attempt a match by email or referral code. If that fails, show a neutral path and push a post-install link to restore context.

Two things that reduced mismatches for me:

  • Post-checkout email includes a restore link that replays context if the app missed it
  • I log context id to the order, so support can fix access in seconds

Small win, big sanity.

We store UTMs server side and fetch on first open. Fewer mismatches now.