Search code examples
javaandroidalarmmanageremulationandroid-doze

Why is doze mode not affecting the AlarmManager setExact() function?


I'm trying to test the behavior of my Android app when the OS goes in Doze mode. I'm using a gennymotion emulator running Android API 25. The application launches an IntentService through the AlarmManager using the method setExact with type RTC_WAKEUP. I set the alarm to fire after 1 minute (only for testing purposes).

This is the intent service code (MyService.java):-

public class MyService extends IntentService {

public static final String TAG = "noor";

@Override
public void onHandleIntent(Intent intent) {
    for (int i = 1; i <= 10; i++) {
        Log.d(TAG, "i: " + i);

        try {
            Thread.sleep(1000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

}

This is the alarm manager code:-

AlarmManager alarm = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
        Intent intent = new Intent(this, MyService.class);
        PendingIntent pendingIntent = PendingIntent.getService(this, 101, intent, 0);
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
            alarm.setExact(AlarmManager.RTC_WAKEUP,System.currentTimeMillis() + (60 * 1000),pendingIntent);
        }

}

just to make sure i succeed in putting the emulator in IDLE state by running the suggested dumpsys commands as following:-

adb shell dumpsys deviceidle enable
adb shell dumpsys battery unplug
adb shell dumpsys deviceidle force-idle

I even double-checked by using

adb shell dumpsys deviceidle get deep

Now here's the problem:-

Even when the device is IDLE I'm still able to see the IntentService(MyService) being launched by the alarm. these are the logcat results:-

    2019-10-04 01:42:20.842 1818-1922/com.example.android.sunshineweatherapp D/noor: i: 1
2019-10-04 01:42:21.843 1818-1922/com.example.android.sunshineweatherapp D/noor: i: 2
2019-10-04 01:42:22.845 1818-1922/com.example.android.sunshineweatherapp D/noor: i: 3
2019-10-04 01:42:23.856 1818-1922/com.example.android.sunshineweatherapp D/noor: i: 4
2019-10-04 01:42:24.857 1818-1922/com.example.android.sunshineweatherapp D/noor: i: 5
2019-10-04 01:42:25.859 1818-1922/com.example.android.sunshineweatherapp D/noor: i: 6
2019-10-04 01:42:26.860 1818-1922/com.example.android.sunshineweatherapp D/noor: i: 7
2019-10-04 01:42:27.861 1818-1922/com.example.android.sunshineweatherapp D/noor: i: 8
2019-10-04 01:42:28.862 1818-1922/com.example.android.sunshineweatherapp D/noor: i: 9
2019-10-04 01:42:29.863 1818-1922/com.example.android.sunshineweatherapp D/noor: i: 10

This should not be the expected behavior according to the docs:-

Standard AlarmManager alarms (including setExact() and setWindow()) are deferred to the next maintenance window.

So I was expecting the opposite as well(since setExact() should not be triggered if the device is on doze mode). I have even tested this on a real device (running Android Marshmallow) and getting the same results.

Is this a bug? Or am I missing something?

The following question might be duplicate but the answer is not given as desired:- Android M (preview) Doze mode and AlarmManager

P.S:-

This is the third time I'm posting this question on this platform since I didn't get any answers. I couldn't find any help throughout the internet (reddit, androidcentral, quora, coderanch).
I have to make an alarm clock app and I won't be able to test the behaviors correctly if this problem persists.


Solution

  • I FOUND THE PROBLEM:

    First and foremost, Doze mode did not affect the alarmmanager setExact() function when i was testing my app in an emulator(i used genymotion in my case).

    I then decided to use a physical phone i.e HTC Desire 530 but the results were still the same. This is where i got frustrated until i found out something very interesting in the HTC official documentation support page which was that:

    The phone exits from Doze mode when:

    You plug in the power adapter and charge the phone.

    There's movement, such as when you pick up the phone.

    An alarm clock goes off at your set time.

    I wondered if the 3rd point could be the cause behind doze mode not effecting the alarmmanager setExact method. So i tested my app in another phone i.e OPPO A3s. This is where things ran as expected !

    The setExact method did not run in doze mode while it did run when i exited the doze mode ! while setExactAndAllowWhileIdle() ran just like its written in the docs.

    So i got to the conclusion that:-

    • HTC might have modified the doze mode behavior ? (since android officially restricts alarmmanager setExact execution in doze mode while HTC doesn't). The reason behind this (maybe naive) assumption is i've seen some un-standard behavior in some android phones like the alarm would go off even when the device was POWERED OFF !
    • and last but not least, never trust your emulator :p

    P.S:

    if you are wondering why am i so concerned with this whole thing, it's because i am working on an alarm app and i am using the alarmmanager for performing time based tasks. I would not have been able to test my app properly if this problem would have persisted (hope you get my point).

    Android's background restrictions and battery optimizations have made simple things complex.

    UPDATE:-

    Doze mode had no effect on the alarmmanager setExact() even when i turned on the battery optimization in HTC Desire 530.