Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Voip Pushkit notification will not re-launch the app if it was force-quitted and device was rebooted

I cannot get voip pushkit notifications to re-launch the app if the user has force-quitted the app (by swiping it up in the multi-tasking interface) AND if the device was rebooted.

However, I can get the voip pushkit notifications to work in the following scenarios:

  • The app was force-quitted then the pushkit notification arrives. The app will be relaunched immediately. Standard push notifications are not capable of waking the app in such scenario.

  • The app was in the background / suspended and the device is rebooted. Thanks to Voip mode, the app will be relaunched on device reboot (I can see the process in Xcode Activity Monitor). There is a trick needed here to get the pushkit notification to be properly processed which is described in http://blog.biokoda.com/post/114315188985/ios-and-pushkit in these terms "Before initializing PushKit start a background task. Finish this task when PushKit token is received"

Somehow when combining these two (device reboot AND app force-quit) then pushkit notifications doesn't seem to relaunch the app. Also when looking at the device logs in Xcode I get no logs from apsd saying the notification was processed by the system.

Here is my code:

@implementation AppDelegate
{
  UIBackgroundTaskIdentifier bgTask;
}
- (BOOL)application:(UIApplication *)application 
    didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
    UIApplication* app = [UIApplication sharedApplication];
    bgTask = [app beginBackgroundTaskWithExpirationHandler:^{
        [app endBackgroundTask:bgTask];
        bgTask = UIBackgroundTaskInvalid;
    }];
    dispatch_async(dispatch_get_global_queue(
    DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        while (true) {
            ;
        }
    });
    // Initialize pushkit
    PKPushRegistry *pushRegistry =
        [[PKPushRegistry alloc] initWithQueue:dispatch_get_main_queue()];
    pushRegistry.delegate = self;
    pushRegistry.desiredPushTypes = [NSSet setWithObject:PKPushTypeVoIP];    
    return YES;
}

- (void)pushRegistry:(PKPushRegistry *)registry 
    didUpdatePushCredentials:(PKPushCredentials *)credentials
    forType:(NSString *)type{
    UIApplication* app = [UIApplication sharedApplication];
    [app endBackgroundTask:bgTask];
    // ... more code to read the token ...
}

- (void)pushRegistry:(PKPushRegistry *)registry
    didReceiveIncomingPushWithPayload:(PKPushPayload *)payload
    forType:(NSString *)type {
    // ... logging to check if notification is received ...
}

Also I have "Voice over IP" and "Remote notifications" enabled in Background modes.

I know other apps like Whatsapp are capable of being relaunched in this scenario, so I don't understand what I am doing wrong.

On a related note, it doesn't help to do the following 1) Force quit 2) Send a pushkit notification - which will be received 3) Reboot. The app will not be relaunched and a new push notification will still not relaunch it.

like image 909
mcaoun Avatar asked Sep 16 '15 08:09

mcaoun


1 Answers

After I tested the app with an AdHoc provisioning profile (and installed it from iTunes), the Voip push notifications served through prod gateway.push.apple.com instead of gateway.sandbox.push.apple.com started waking up the force-quitted app after reboot.

The os is apparently handling development and production in a different manner.

Looking further into the APSD logs, I found that when using a development provisioning profile the following is printed out:

: XXXX-XX-XX XX:XX:XX +0300 apsd[97]:
These enabled topics have been removed {( "YOUR_BUNLE_IDENTIFIER" )}

This does not happen when using an adhoc provisioning profile.

like image 141
mcaoun Avatar answered Oct 18 '22 13:10

mcaoun