Summarize this documentation using AI
Overview
If you want in-session conversion lifts (not just inbox nudges), Customer.io in-app messages are one of the cleanest ways to do it—assuming your SDK tracking is tight. If you’re trying to map this into a real retention program quickly, you can book a strategy call and we’ll pressure-test your identity + event plan before you ship something that undercounts or spams.
In practice, in-app works best when it’s treated like an extension of your event taxonomy: a message is just a response to a high-intent behavior (viewed product, started checkout, stalled, came back) and a known identity state (anonymous vs logged in, new vs returning, VIP vs discount-only).
How It Works
In-app messages only perform when Customer.io can reliably answer two questions in real time: “who is this?” and “what did they just do?” That’s why SDK setup matters more than creative—your install, identify calls, and event payloads determine whether messages trigger at the right moment and whether attribution is believable.
- SDK initializes on app/web load: your app boots the Customer.io SDK as early as possible so it can observe sessions and receive in-app message payloads.
- Anonymous activity is captured first: a shopper can browse and even add to cart before logging in. You want that activity recorded, not lost.
- Identity stitching happens on login/signup: when the user authenticates, your app makes an
identifycall with a stable identifier (usually your internal customer ID) and key attributes. This is where anonymous browsing gets tied back to the person profile. - Events drive targeting and timing: you send events like
Product Viewed,Added to Cart,Checkout Started,Order Completed, andApp Opened. Journeys/segments then decide who should see an in-app message and when. - Device context matters: in-app is inherently device/session-based. If the same person uses multiple devices, your identify strategy determines whether they get the right message on the right device—or duplicates across devices.
Step-by-Step Setup
The fastest path is: install the SDK, get identity correct, then layer in events that map to revenue moments. Don’t start by building messages—start by proving your events and stitching in the activity log.
- Install the Customer.io SDK (mobile or web) and initialize early.
Initialize on app start / first page load so sessions and in-app payload delivery work reliably. - Decide your primary identifier and enforce it everywhere.
Use a stable ID (e.g.,customer_id) rather than email as the primary key. Email changes; IDs don’t. Keep email as an attribute. - Send an
identifycall at authentication.
On login/signup, callidentifywith your stable ID and set core attributes you’ll segment on (email, phone, acquisition source, first_order_date, total_orders, last_order_date, etc.). - Capture anonymous browsing events before login.
Track product and cart behavior even when the user is anonymous. Then confirm those events appear under the identified profile after login (this is where most programs quietly break). - Implement a minimal retention event taxonomy.
Start with:Product Viewed(product_id, category, price)Added to Cart(product_id, quantity, cart_value)Checkout Started(cart_value, item_count)Order Completed(order_id, revenue, items)App Opened/Session Started(optional but helpful for gating frequency)
- Validate event ordering and deduplication.
Make sureOrder Completedfires once per order and that cart events don’t double-fire on back/forward navigation or app resume. - Create segments that mirror real intent states.
Examples: “Added to cart in last 2 hours AND no order,” “Viewed product 3+ times in 7 days AND no purchase,” “Lapsed 60+ days AND app opened today.” - Launch one in-app message tied to one event.
Keep your first message simple so you can debug tracking: one trigger, one audience, one suppression rule, one goal.
When Should You Use This Feature
In-app messages earn their keep when the user is already present and you can change the outcome of the session. If you’re trying to rescue a session that’s slipping or push a second purchase at the right moment, in-app is often more efficient than email/SMS.
- Cart recovery while the shopper is still active: if someone triggers
Checkout Startedand then stalls, an in-app prompt can address friction (shipping threshold, returns, pay-in-4) before they bounce. - Repeat purchase acceleration: after
Order Completed, use in-app on the next session to recommend replenishment timing, bundles, or complementary SKUs—especially for consumables. - Reactivation when lapsed users return to the app: when a 60–90 day lapsed customer opens the app, in-app can deliver a “welcome back” offer without training your whole list to wait for email discounts.
- Product discovery nudges: if they view the same PDP multiple times, in-app can push social proof, UGC, or a comparison guide—things that don’t belong in a push notification.
Real D2C scenario: A skincare brand sees high “add to cart” but low checkout completion on mobile. They track Added to Cart and Checkout Started. If Checkout Started fires and no Order Completed within 10 minutes, the next app screen shows an in-app message: “Free shipping over $45 — you’re $8 away” with a one-tap add-on. This only works if cart_value is accurate and identity is stitched when the user logs in mid-checkout.
Operational Considerations
Most retention programs don’t fail because the message is ugly—they fail because segmentation, data flow, and orchestration don’t match how the app actually behaves. Treat in-app as a real-time channel with strict guardrails.
- Segmentation depends on event freshness: if events arrive late (batching, poor connectivity), you’ll show the wrong message. For in-app, prioritize near-real-time event delivery where possible.
- Identity stitching is the difference between “helpful” and “creepy”: if you identify too early (before consent) or too late (after key events), your audiences won’t match the session reality.
- Suppressions need to exist across channels: if SMS is already chasing the same cart, don’t also hammer them in-app. Build shared suppression logic (recent message seen, recent purchase, customer service flags).
- Frequency control should be event-based, not calendar-based: e.g., “max 1 cart in-app per 24h” and “never show post-purchase upsell within 30 minutes of order confirmation.”
- Orchestration reality: in-app triggers often compete with paywalls, onboarding modals, and app update prompts. Coordinate with product so your message isn’t hidden behind competing UI layers.
Implementation Checklist
Before you scale in-app messages beyond a single use case, run through this checklist so you don’t build a retention program on shaky tracking.
- SDK initialized early and consistently across app versions
identifycalled on login/signup with a stable customer ID- Anonymous events captured and successfully stitched post-login
- Core commerce events implemented with clean payloads (IDs, value, currency)
- Event deduplication in place for checkout and purchase
- Segments built from events + attributes (not “all users”)
- Cross-channel suppressions defined (email/SMS/push/in-app)
- QA plan: test users, test devices, and a repeatable test script
Expert Implementation Tips
These are the patterns that consistently improve performance and reduce weird edge cases once you’re live.
- Log identity state in your event payloads during QA. During testing, include a debug flag like
is_logged_in(or validate via your app logs) so you can tell whether the right user state triggered the message. - Use “thin” events and enrich later if needed. For in-app triggers, you mostly need IDs and totals. Don’t ship massive product JSON if it slows delivery or increases failure rates.
- Gate offers by customer value, not just behavior. A high-AOV repeat buyer who stalls at checkout often needs reassurance (returns, shipping speed), not a discount. Your identify attributes (total_orders, total_spent) make that possible.
- Design for session timing. If your app commonly backgrounds/resumes, ensure events fire on resume in a controlled way so you don’t retrigger the same in-app message repeatedly.
Common Mistakes to Avoid
Most teams make the same few mistakes when they rush to “launch in-app” without treating the SDK as part of their retention infrastructure.
- Using email as the primary identifier. It creates duplicates when users change emails or use Apple Private Relay. Use a stable internal ID and store email as an attribute.
- Firing
identifyon app open for logged-out users. That can attach activity to the wrong profile on shared devices and ruins stitching integrity. - Double-firing purchase events. If
Order Completedfires twice, you’ll suppress the wrong people, inflate revenue attribution, and break post-purchase flows. - No suppression after conversion. If someone completes checkout and still sees a cart recovery in-app because the purchase event arrived late, trust drops fast.
- Launching too many messages at once. In-app is easy to spam because it “doesn’t cost per send.” Start with one revenue moment, validate, then expand.
Summary
If your SDK identity and event tracking are clean, in-app messages become a reliable lever for cart recovery, repeat purchase, and lapsed-user reactivation while the customer is actively shopping.
If tracking is messy, you’ll get mistimed prompts, duplicate targeting, and attribution you can’t trust—fix the plumbing first, then scale.
Implement In App with Propel
If you’re already running retention in Customer.io, the main lift is getting the SDK events and identity stitching to match how your storefront/app really behaves (anonymous browse → login → checkout → purchase). When teams want to move faster without breaking tracking, we’ll usually map the event taxonomy, define suppression rules, and QA the end-to-end flow across devices—then you can book a strategy call to sanity-check your implementation plan before you roll it out.