AlarmManager repeating alarm missing randomly when phone is not in use

前端 未结 3 2013
南旧
南旧 2021-02-05 22:24

I am calling a background Service at interval of 30 min to read the latitude/longitude of current location and sending it to server by POST API .

I am using

3条回答
  •  我在风中等你
    2021-02-05 22:55

    The problem might be your PendingIntent calling a Service. The device can go back to sleep before your Service finishes (or even starts) execution.

    I'd suggest you to use a BroadcastReceiver instead (since a WakeLock is guaranteed during onReceive()).

    Acquire a WakeLock in onReceive(), start your Service from there and release the WakeLock from the Service, when appropriate.

    To simplify this process you can use the WakefulBroadcastReceiver helper class:

    1. Call PendingIntent.getBroadcast() instead of PendingIntent.getService().
    2. Start an IntentService from onReceive() by calling WakefulBroadcastReceiver.startWakefulService().
    3. Do your stuff in onHandleIntent() and call WakefulBroadcastReceiver.completeWakefulIntent() when finished.

    For example, a BroadcastReceiver that starts a wakeful Service:

    public class ExampleReceiver extends BroadcastReceiver {
        @Override
        public void onReceive(Context context, Intent intent) {
            Intent wakefulServiceIntent = new Intent(context,
                ExampleWakefulService.class);
    
            WakefulBroadcastReceiver.startWakefulService(context,
                wakefulServiceIntent);
        }
    }
    

    And the Service:

    public class ExampleWakefulService extends IntentService {
    
        private static final String NAME = "com.example.ExampleWakefulService";
    
        public ExampleWakefulService() {
            super(NAME);
        }
    
        @Override
        protected void onHandleIntent(Intent intent) {
    
            // doing stuff
    
            WakefulBroadcastReceiver.completeWakefulIntent(intent);
        }
    }
    

    Also, check out this article from the developer's guide on keeping the device awake.

    On API level 23+ you have to deal with Doze.

    From the documentation:

    To help with scheduling alarms, Android 6.0 (API level 23) introduces two new AlarmManager methods: setAndAllowWhileIdle() and setExactAndAllowWhileIdle(). With these methods, you can set alarms that will fire even if the device is in Doze.

    Unfortunately there is no alternative for setRepeating(), so you have two choices:

    • Set exact alarms (using the appropriate method depending on the API level of the device, check out this answer for an example) and reschedule them every time they fire.
    • Whitelist your app (not recommended because of the strict revision policy of Google).

提交回复
热议问题