Mobile Application Monetization: IAP, Subscriptions and Ad Mediation
An application with poorly implemented purchases loses money not because users don't want to pay, but because StoreKit transaction hangs, Receipt Validation fails with an error, or restore purchases doesn't work — and the user writes to support or leaves 1 star.
In-App Purchases and StoreKit 2
StoreKit 2 (iOS 15+) — modern API with async/await and verified transactions on device side without server. Transaction.currentEntitlements returns all active purchases. Key change compared to StoreKit 1: JWS signature verification on device via VerificationResult<Transaction> — no need to send receipt to server for basic verification.
But server-side validation is still needed for consumable purchases and fraud protection. App Store Server API replaces the old /verifyReceipt endpoint. Webhooks via App Store Server Notifications v2 provide real-time events: SUBSCRIBED, DID_RENEW, EXPIRED, REFUND — without polling.
Typical mistake: not handling paymentQueue(_:updatedTransactions:) in the background for incomplete transactions. User bought consumable, application crashed before finishTransaction — purchase hangs in queue, on next launch is restored and requires re-processing on server. Without server idempotency — double charging.
Subscriptions: Lifecycle Management
Subscription model requires tracking states: trial → active → grace period → expired → refunded. RevenueCat is the de facto standard for subscription management in production. Abstracts StoreKit and Google Play Billing, provides unified API, webhooks, cohort analytics and A/B paywall testing.
Alternative to RevenueCat — own implementation with Adapty or Qonversion. Fully custom — only if there are reasons (data must not leave infrastructure, non-standard logic).
Google Play Billing Library 6+ requires handling PurchasesUpdatedListener and explicit acknowledgePurchase() or consumePurchase() call within 3 days — otherwise Google automatically cancels the purchase and refunds the money.
Ad Mediation
Showing ads through one source means losing revenue. Mediation (waterfall or bidding) requests ads from multiple networks and shows the best bid.
Google AdMob — foundation: banner, interstitial, rewarded. Mediation via AdMob Mediation or MAX (AppLovin) — the second de facto standard. MAX uses In-App Bidding — real-time auction without waterfall. In practice, MAX delivers CPM 15-30% higher than classic waterfall (depends on geo and audience).
ironSource (Unity Ads) — strong position in gaming segment, especially rewarded video. Mintegral — good coverage of Asian audience.
Mediation setup requires ATT (App Tracking Transparency) on iOS 14+. Without requestTrackingAuthorization, ad CPM drops 3-5x for non-consenting users. SKAdNetwork and Privacy Manifest (iOS 17) — mandatory requirements without which review fails.
Freemium: Model Design
Freemium works when the boundary between free and paid is drawn correctly. Too strict paywall at start — user deletes. Too generous free tier — no incentive to pay.
Pattern that works technically: feature flags from server (Remote Config in Firebase or LaunchDarkly) manage access to features. This allows A/B testing paywall without release, changing trial conditions, running promotions.
Implementation at code level: EntitlementManager — single point of feature access verification that knows about subscription status, flags and promos. No scattered isPremium checks throughout code.
Timeline: basic IAP integration with StoreKit 2 or Google Play Billing — 1-2 weeks. Full subscription system with RevenueCat, paywall screens, analytics and webhooks — 3-5 weeks. Ad mediation with MAX and 3-4 networks — 1-2 weeks.







