Tuesday, March 15, 2016

Performing recurring tasks in Android (Periodically refreshing location)

When writing an Android app, you often need to perform periodical tasks, such as calling a (remote) API, getting the current (last known) position of the device, or notify the user of something.

First step: Schedule an Alarm

You'll want the Alarm to look something like this:



What this will do, is make sure, that the AlarmManager fires the defined Intent (PendingIntent) in a scheduled timeframe. In our example, it is fired roughly every minute. You should prefer setInexactRepeating() to multiple setExact() calls whenever possible, as this will reduce battery strain, at the cost of some inaccuracy in the wanted interval. Also, if you can allow even more inaccuracy in the frequence of Alarm calls, make sure to use ELAPSED_REALTIME (or RTC as needed) instead of ELAPSED_REALTIME_WAKEUP to further prolong battery life.

Now, this code still needs to be called from somewhere. A place to start would be if the user opens the App in the current session, so the onCreate() method of your Activity opened on App start would be a good place to start. Make sure to unregister the Alarm appropriately if you only need it active while your App is open or in the foreground. Since we need to know the user's location even if he did not start the App on that day yet, we furthermore register an Alarm at Bootup of the device, which will requre a special permission:


Second step: Start your service

Make sure to add the required permissions in your AndroidManifest.xml, as well as register both the BootReceiver, and an AlarmReceiver which will trigger whenever the Alarm goes off.

Third step: Do your work in your service

We use Google's FusedLocationProvider, which takes several factors into account to give you the last known location. Set Intervals, number of Updates you want and Accuracy according to your needs and connect the client. You can then go ahead and perform your work (like FusedLocationApi.getLastLocation()) in the onConnected() method of your service.

Additional comments


Schedule your Alarm once: Make sure to register your Alarm only once, either at startup or when the app is launched. The Android system handles it well if you schedule the alarm multiple times accidentally, and does not schedule it more than once for you, but still you should not rely on this behaviour staying the same for all future Android versions.

One word of caution regarding network API Calls: Do not perform brainless polling, as you'll stress out the network and battery very quickly. Make sure you determine in your logic, wether an API request is needed, and only then perform the call. Also make sure to add some randomness or different intervals for scheduled API calls, as you do not want to have all your users (and hopefully you'll have a lot) hit your API at the same time.

No comments:

Post a Comment