Hezron
Hezron

Reputation: 352

Trigger background sync using notification when app not runnning

I already implemented this:

In Apple docs on Push Notification, they are saying:

When a silent notification arrives, iOS wakes up your app in the background so that you can get new data from your server or do background information processing.

#

(void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo fetchCompletionHandler:(void (^)(UIBackgroundFetchResult))completionHandler

After receive silent notification. In this method, I am downloading some data from the server then data synchronization.

EXPECTED:

The goal is when user open/using the app, it should reflect the latest position for the user.

ACTUAL:

Receive silent notification, download data from server, then data synchronization are works fine when app is running in foreground and background.

But can't wakes up the app in background and to do that when my app is not in running state (app is not launched or killed from app switcher).

QUESTION:

I silent notification doesn't work when app not running? (can't wake up app in background)

Is there missing code in my code which need implemented?

If this way doesn't work when app not running. Is there any way to keep my app local data always same/synced with the database server (when I'm using or not the app)? how other app do it?

Upvotes: 2

Views: 1508

Answers (1)

Aleksander
Aleksander

Reputation: 2815

Silent notifications are able to bring your app into the background to do any tasks that you may require, as per the Apple documentation:

the system wakes the app in the background (or launches it into the background)

The method you are using, userNotificationCenter:didReceiveNotificationResponse:withCompletionHandler:, is called to let your app know which action was selected by the user for a given notification.

The correct method you should be implementing (even in iOS10) is: application:didReceiveRemoteNotification:fetchCompletionHandler:. This tells the app that a remote notification arrived that indicates there is data to be fetched.

The way you are doing it is the correct (and probably most popular way) of syncing data between a server and application instance when the user is not actively engaging with the app. Your issue seems to be that you are using the wrong app delegate instance method for your callback.

Update 1:

As per your updated question, I have updated my answer.

That the notifications are not being delivered to your app after it has been terminated by the user is by design. According to the documentation:

The system does not automatically launch your app if the user has force-quit it. In that situation, the user must relaunch your app or restart the device before the system attempts to launch your app automatically again.

To combat this, you can look into Apple PushKit. Originally intended for VoIP apps, it would also work for your application. However unlike regular silent notifications, these do wake up your app even if it has been terminated by the user.

However, keep in mind that once a user terminates an application he expects to have terminated it for good (or until he manually restarts it). To override this would be poor design. Maybe it is fine with the user if the app spends some time downloading the latest data upon launch if the user had terminated the app previously? Depending on the exact reason why you need your app to have the latest information before launch, maybe you don't need to account for this scenario.

Upvotes: 1

Related Questions