How to Prevent Alarms from Being Skipped with AlarmManager setExactAndAllowWhileIdle Method?

fatih uyanık 245 Reputation points
2025-09-22T06:02:41.63+00:00

Hello.

I'm developing an Android app with Net MAUI. This app announces the time every hour with a ticking timer. I use the AlarmManager.setExactAndAllowWhileIdle method. While it works without any shift at the hour on Samsung devices, on some devices, the announcements don't appear at all. There's a 2 to 5 minute delay.

I've done a lot of research, but I haven't been able to figure out how to fix this issue.

How can I configure this so that it announces at the exact time without skipping?

Could you help me with this?

Thank you.

Developer technologies | .NET | .NET Multi-platform App UI

1 answer

Sort by: Most helpful
  1. Anonymous
    2025-09-22T07:26:15.1933333+00:00

    Hello @fatih uyanık !

    If you're using alarmManager.SetExactAndAllowWhileIdle(...) to trigger hourly announcements in your MAUI Android app but are seeing 2–5 minute delays or missed alarms. This isn't a bug in your code, it result of Android’s power management and OEM customizations, please refer to this link for more detail:

    https://developer.android.com/training/monitoring-device-state/doze-standby

    On Android 6.0+, when the device is idle (screen off, not charging), Android enters Doze mode and batches alarms to conserve battery. setExactAndAllowWhileIdle() bypasses some batching, but not all, especially if alarms are frequent. Android enforces a minimum interval between exact‑while‑idle alarms (often ~15 minutes) in deep idle.


    If you want hourly, on‑the‑dot announcements without drift or skips, across all devices, here are the steps you can follow:

    1. Request the right permissions: On Android 12+, you must declare:
         <!-- Exact alarms (API 31+) -->
         <uses-permission android:name="android.permission.SCHEDULE_EXACT_ALARM" />
         <!-- Only if you will guide user to ignore battery optimizations -->
         <uses-permission android:name="android.permission.REQUEST_IGNORE_BATTERY_OPTIMIZATIONS" />
      
    2. Use the right alarm type: Use AlarmType.RtcWakeup so the device wakes up to deliver the alarm.
    3. Reschedule manually: Don’t use setRepeating(), it’s not exacted in Doze mode. Instead, when the alarm fires, you can calculate the next top‑of‑hour and schedule it again.
         // Compute next top-of-hour (wall clock) using local time
         var now = DateTime.Now;
         var next = new DateTime(
            now.Year, now.Month, now.Day, now.Hour, 0, 0, DateTimeKind.Local
         ).AddHours(1);
       
         // Convert to epoch ms (UTC) for AlarmManager.RtcWakeup
         long triggerAtMillis = (long)(next.ToUniversalTime() -
            DateTime.UnixEpoch).TotalMilliseconds;
       
         // Reuse a stable PendingIntent (FLAG_UPDATE_CURRENT)
         alarmManager.SetExactAndAllowWhileIdle(
            AlarmType.RtcWakeup,
            triggerAtMillis,
            pendingIntent
         );
      
    4. Run work in a foreground service: When the alarm fires, you can start a short‑lived foreground service to do the announcement and stop it immediately after work is done. This helps prevent the OS from killing your task mid‑execution.
    5. Request Battery Optimization Exemption: This tells Android not to defer your alarms when idle
         var intent = new Intent(Android.Provider.Settings.ActionRequestIgnoreBatteryOptimizations);
         intent.SetData(Android.Net.Uri.Parse("package:" + context.PackageName));
         context.StartActivity(intent);
      

    Even with all of these measures, Android does not guarantee millisecond‑accurate delivery during deep idle. On devices with aggressive OEM restrictions, small delays may still occur unless the app is explicitly whitelisted. You can refer to dontkillmyapp.com for device-specific guidance, if core functionality is affected, you may guide users to:

    • Enable the app’s Auto‑start / Allow background start
    • Lock / pin the app in Recents (prevents aggressive cleanup)
    • Disable battery optimization, app sleeping, or background restrictions for the app.

    Please note that effectiveness varies by OEM and is not guaranteed.


    I hope this helps! Let me know if you have any questions, I’m happy to answer! If you find this answer useful, feel free to mark this as final answer!

    Was this answer helpful?


Your answer

Answers can be marked as 'Accepted' by the question author and 'Recommended' by moderators, which helps users know the answer solved the author's problem.