Setting Up iOS Uninstall Tracking

iOS Uninstall Tracking Setup

Track app uninstalls on iOS to measure user retention, identify low-quality traffic sources, and optimize campaign performance using Apple Push Notification service (APNs) integration with Singular SDK.


Overview

How Uninstall Tracking Works

Singular detects iOS app uninstalls by sending silent push notifications via Apple Push Notification service and monitoring delivery responses to determine if the app remains installed on devices.

Technical Process:

  1. Token Registration: Singular SDK registers APNs device tokens with Singular servers
  2. User Opt-In: Users grant push notification permissions when prompted by iOS
  3. Silent Notifications: Singular sends periodic silent push notifications to registered devices
  4. Delivery Feedback: APNs reports delivery success or failure
  5. Uninstall Detection: Failed deliveries indicate app uninstall
  6. Event Recording: Uninstall event attributed to original install source

Requirements

  • SDK Version: iOS SDK 8.0+ required for uninstall tracking
  • APNs Certificate: Production SSL certificate from Apple Developer account
  • Push Notification Support: App must implement APNs registration and token handling
  • User Consent: Users must opt in to push notifications for tracking to work
  • App Update: Users must install updated app version with uninstall tracking enabled

Important Considerations

User Opt-In Requirement: In accordance with Apple's policies, users must explicitly opt in to receive push notifications. Singular can only track uninstalls for users who have granted notification permissions.

Key Points:

  • Silent Notifications: Singular's uninstall tracking uses silent push notifications that do not display any visible alerts to users
  • Attribution Preservation: Uninstalls are tracked as events without removing the original attribution link. Users may uninstall and reinstall multiple times, potentially resulting in uninstall rates exceeding 100%
  • Batch Processing: Uninstall detection is batch-based, relying on APNs response feedback. Expect up to 24 hours for uninstall data to appear in Singular dashboard
  • Permission Dependencies: Tracking coverage directly correlates with push notification opt-in rate. Apps with low opt-in rates will have incomplete uninstall data
  • Network Dependency: Silent push notifications require active network connection. Devices offline for extended periods may delay uninstall detection

Setup Instructions

Configure iOS uninstall tracking by integrating Singular SDK, implementing Apple Push Notifications, and uploading APNs certificates to Singular.

Step 1: Integrate iOS SDK 8.x+

Update SDK Version

Upgrade to iOS SDK 8.0 or higher to enable uninstall tracking functionality.

CocoaPods Installation:

Podfile
platform :ios, '12.0'
use_frameworks!

target 'YourApp' do
  # Singular iOS SDK
  pod 'Singular-SDK', '~> 12.6.2'
end

Swift Package Manager:

Xcode
// File > Add Package Dependencies
// Enter repository URL:
https://github.com/singular-labs/Singular-iOS-SDK

// Select version: 12.6.2 or later

Complete integration guide: iOS SDK Integration Guide


Step 2: Configure Apple Push Notifications

Enable Push Notification Capability

Add push notification capability to your Xcode project and implement APNs registration in your app.

Xcode Configuration:

  1. Open Project Settings: Select your project in Xcode navigator
  2. Select Target: Choose your app target
  3. Add Capability: Go to Signing & Capabilities tab
  4. Enable Push: Click "+ Capability" and add "Push Notifications"
  5. Background Modes: Enable "Remote notifications" under Background Modes capability

First Time Setup: If this is your first time implementing push notifications for iOS, see the comprehensive Apple Push Notification Service (APNs) Setup Guide.


Implement APNs Registration

Add code to register for push notifications and pass the APNs device token to Singular SDK.

Swift
import UIKit
import UserNotifications
import Singular

@main
class AppDelegate: UIResponder, UIApplicationDelegate {
    
    func application(_ application: UIApplication, 
                     didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
        
        // Request push notification permissions
        requestPushNotificationPermissions()
        
        // Initialize Singular SDK
        let config = SingularConfig(apiKey: "YOUR_API_KEY", secret: "YOUR_SECRET")
        Singular.start(config)
        
        return true
    }
    
    func requestPushNotificationPermissions() {
        let center = UNUserNotificationCenter.current()
        center.requestAuthorization(options: [.alert, .sound, .badge]) { granted, error in
            if granted {
                print("Push notification permission granted")
                DispatchQueue.main.async {
                    UIApplication.shared.registerForRemoteNotifications()
                }
            } else {
                print("Push notification permission denied")
            }
        }
    }
    
    // Called when APNs successfully registers device
    func application(_ application: UIApplication, 
                     didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data) {
        
        // Pass token to Singular for uninstall tracking
        Singular.registerDeviceToken(forUninstall: deviceToken)
        
        // Convert token to hex string for logging
        let tokenString = deviceToken.map { String(format: "%02.2hhx", $0) }.joined()
        print("APNs device token registered: \(tokenString)")
    }
    
    // Called if APNs registration fails
    func application(_ application: UIApplication, 
                     didFailToRegisterForRemoteNotificationsWithError error: Error) {
        print("Failed to register for remote notifications: \(error.localizedDescription)")
    }
    
    // Handle incoming push notifications
    func application(_ application: UIApplication,
                     didReceiveRemoteNotification userInfo: [AnyHashable : Any],
                     fetchCompletionHandler completionHandler: @escaping (UIBackgroundFetchResult) -> Void) {
        
        // Pass notification data to Singular
        Singular.handleNotification(userInfo)
        
        completionHandler(.newData)
    }
}

iOS 13+ Requirements: Starting with iOS 13, you must call registerForRemoteNotifications() on the main thread after receiving authorization. Use DispatchQueue.main.async as shown above.

Complete implementation guide: Singular iOS SDK Implementation Guide


Step 3: Create Apple Push Notification Certificate

Generate APNs SSL Certificate

Create a Production SSL certificate in your Apple Developer account to enable Singular to send push notifications for uninstall tracking.

  1. Open Apple Developer Portal: Navigate to Apple Developer
  2. Access Certificates: Go to Certificates, Identifiers & Profiles
  3. Select Identifiers: Click Identifiers in left sidebar
  4. Choose App ID: Select your app's identifier from the list
  5. Configure Push Notifications: Scroll to Application Services and locate Push Notifications
  6. Create Certificate: Click "Configure" next to Push Notifications
  7. Select Type: Choose "Apple Push Notification service SSL (Sandbox & Production)" for Production certificate

Certificate Type Requirement: Singular uninstall tracking requires the Production SSL certificate for live apps. Development certificates can only be used for internal testing.


Create Certificate Signing Request (CSR)

Generate a CSR on your Mac to create the APNs certificate.

  1. Open Keychain Access: Launch Keychain Access app on your Mac
  2. Request Certificate: Keychain Access menu → Certificate Assistant → Request a Certificate From a Certificate Authority
  3. Enter Email: Provide your email address
  4. Common Name: Enter a descriptive name (e.g., "YourApp Push Notifications")
  5. Save to Disk: Select "Saved to disk" option
  6. Continue: Click Continue to save the CSR file

Upload CSR and Download Certificate

Upload your CSR to Apple Developer portal to generate the APNs SSL certificate.

  1. Upload CSR: In Apple Developer portal, upload the CSR file you created
  2. Generate Certificate: Click Continue to generate the certificate
  3. Download Certificate: Download the generated .cer file
  4. Install Certificate: Double-click the .cer file to add it to your Mac Keychain

Step 4: Export Certificate as .p12 File

Generate P12 from Keychain

Export your APNs certificate and private key from Keychain as a .p12 file to upload to Singular.

  1. Open Keychain Access: Launch Keychain Access app
  2. Select Certificate: In "My Certificates" category, locate your APNs certificate
  3. Expand Certificate: Click disclosure triangle to reveal the private key paired with the certificate
  4. Select Both Items: Hold Command and click both the certificate and private key to select them
  5. Export: Right-click and choose "Export 2 items..."
  6. Save as P12: Choose .p12 format and save with a meaningful filename (e.g., "YourApp_APNs_Production.p12")
  7. Set Password: Enter a password to protect the .p12 file (you'll need this password when uploading to Singular)
  8. Confirm: Click OK to export the file

Security Note: Store your .p12 file securely and remember the password. You'll need both to upload the certificate to Singular. Do not share these credentials publicly.


Step 5: Upload Certificate to Singular

Configure Singular App Settings

Upload your .p12 certificate file to Singular's app configuration to enable uninstall tracking.

  1. Open Singular Apps: Navigate to Singular Apps Page
  2. Select App: Choose your iOS app from the list
  3. Advanced Settings: Scroll to Advanced Settings section
  4. Uninstall Tracking: Locate Uninstall Tracking configuration
  5. Upload Certificate: Click "Choose File" and select your .p12 file
  6. Enter Password: Input the password you created when exporting the .p12 file
  7. Save Configuration: Click Save to apply settings

iOS Uninstall Tracking Configuration

Verification: After uploading, Singular will validate the certificate. If validation fails, verify you're using the Production certificate and the password is correct.


Testing Uninstall Tracking

Verify uninstall tracking is configured correctly before releasing updated app to production.

Test Procedure

Validation Steps

  1. Install Test Build: Deploy app with uninstall tracking enabled to test device
  2. Grant Permissions: Launch app and accept push notification permissions when prompted
  3. Verify Registration: Check Xcode console for APNs device token registration message
  4. Confirm SDK Registration: Verify SDK logs show successful token registration with Singular
  5. Wait for Batch Process: Allow 24-48 hours for Singular to send first silent notification
  6. Uninstall App: Delete app from test device
  7. Monitor Dashboard: Check Singular dashboard after 24-48 hours for uninstall event

Testing Timeline: Uninstall tracking is batch-based and may take up to 48 hours to detect and report uninstalls. This delay is expected behavior.


Xcode Console Verification

Check Xcode console output for Singular SDK messages confirming proper configuration.

Expected Log Messages:

[Singular] APNs device token registered successfully
[Singular] Uninstall tracking enabled
[Singular] Device token sent to Singular servers

Common Issues

Issue Cause Solution
Push permission dialog not appearing Permission already denied or not requested Reset permissions: Settings → General → Transfer or Reset iPhone → Reset → Reset Location & Privacy
No device token generated Push Notifications capability not enabled Verify Push Notifications is enabled in Xcode Signing & Capabilities
Registration fails with error Missing or incorrect provisioning profile Ensure provisioning profile includes Push Notifications entitlement
Certificate validation fails in Singular Wrong certificate type or expired certificate Verify you're using Production SSL certificate and it hasn't expired
Token not reaching Singular SDK not initialized or network connectivity issue Ensure Singular.start() is called before registerDeviceToken()
Uninstalls not appearing in dashboard User didn't grant push permissions Uninstall tracking only works for users who opted in to notifications

Simulator Limitations

Physical Device Required: APNs device token generation does not work in iOS Simulator. You must test uninstall tracking on physical iOS devices.


Optimizing Push Notification Opt-In Rates

Maximize uninstall tracking coverage by improving the percentage of users who grant push notification permissions.

Best Practices

Pre-Permission Prompts

Display custom in-app explanations before showing iOS system permission dialog to increase acceptance rates.

  • Explain Value: Clearly communicate benefits users receive from enabling notifications
  • Timing: Request permission at contextually relevant moments when users understand the value
  • Custom UI: Show custom dialog with "Allow" and "Not Now" buttons before system prompt
  • Retry Logic: If user declines, prompt again later after they've experienced app value

Implementation Example

Swift
class NotificationManager {
    
    func showPrePermissionPrompt() {
        // Check if permission already requested
        UNUserNotificationCenter.current().getNotificationSettings { settings in
            if settings.authorizationStatus == .notDetermined {
                DispatchQueue.main.async {
                    self.displayCustomPrompt()
                }
            }
        }
    }
    
    private func displayCustomPrompt() {
        let alert = UIAlertController(
            title: "Stay Updated",
            message: "Enable notifications to receive important updates about your orders and exclusive offers.",
            preferredStyle: .alert
        )
        
        alert.addAction(UIAlertAction(title: "Enable Notifications", style: .default) { _ in
            self.requestSystemPermission()
        })
        
        alert.addAction(UIAlertAction(title: "Not Now", style: .cancel) { _ in
            // User declined - mark for retry later
            UserDefaults.standard.set(Date(), forKey: "last_notification_prompt")
        })
        
        // Present from root view controller
        UIApplication.shared.keyWindow?.rootViewController?.present(alert, animated: true)
    }
    
    private func requestSystemPermission() {
        UNUserNotificationCenter.current().requestAuthorization(options: [.alert, .sound, .badge]) { granted, error in
            if granted {
                DispatchQueue.main.async {
                    UIApplication.shared.registerForRemoteNotifications()
                }
            }
        }
    }
}

Contextual Permission Requests

Effective Timing Strategies:

  • After First Transaction: Request after user completes first purchase or meaningful action
  • Feature Introduction: Prompt when introducing notification-dependent features
  • Value Demonstration: Request after user experiences value from the app
  • Avoid First Launch: Don't request on first app open before users understand app value

Analyzing Uninstall Data

Use iOS uninstall data in Singular reports to optimize campaign performance and identify traffic quality issues.

Available Metrics

Uninstall Tracking Metrics

  • Uninstall Count: Total number of app uninstalls detected
  • Uninstall Rate: Percentage of installs that resulted in uninstalls
  • Trackable User Rate: Percentage of users who opted in to push notifications
  • Days to Uninstall: Average time between install and uninstall events
  • Uninstalls by Source: Breakdown of uninstalls by campaign, publisher, creative
  • Cohort Analysis: Uninstall patterns across different user cohorts

Coverage Considerations

Tracking Coverage: iOS uninstall tracking only covers users who granted push notification permissions. Monitor your app's notification opt-in rate to understand uninstall tracking coverage percentage.

Coverage Calculation:

Tracking Coverage % = (Users with Push Enabled / Total Installs) × 100

Use Cases

Campaign Optimization:

  • Identify campaigns driving low-quality traffic with high uninstall rates
  • Compare uninstall rates across different traffic sources
  • Optimize bidding strategies based on predicted user retention
  • Adjust creative messaging to attract higher-quality users

Fraud Detection:

  • Detect abnormal uninstall patterns indicating install fraud
  • Flag publishers with suspiciously high uninstall rates
  • Monitor time-to-uninstall for signs of bot traffic
  • Identify click injection patterns through rapid uninstalls

User Retention Analysis:

  • Track app stickiness and engagement over time
  • Correlate uninstalls with app updates or feature releases
  • Identify factors contributing to user churn
  • Segment uninstall rates by user demographics and behavior

Best Practices

Optimization Strategies

  • Set Benchmarks: Establish acceptable uninstall rate thresholds for different campaign types
  • Monitor Trends: Track uninstall rates over time to identify seasonal patterns or anomalies
  • Segment Analysis: Compare uninstall rates across user demographics, geographies, and devices
  • Attribution Windows: Consider uninstall timing when evaluating campaign performance
  • Quality Scoring: Incorporate uninstall rates into traffic quality scoring models
  • Coverage Tracking: Monitor notification opt-in rates to understand data completeness
  • Comparative Analysis: Compare iOS vs Android uninstall patterns for platform-specific insights