When my app starts, I want it to check if a particular alarm (registered via AlarmManager) is already set and running. Results from google seem to indicate that there is no way to do this. Is this still correct? I need to do this check in order to advise the user before any action is taken to create a new alarm.
-
8Please validate the answer that solved your issue or post your own solution. – Anis LOUNIS aka AnixPasBesoin Jan 16 '17 at 22:13
13 Answers
Following up on the comment ron posted, here is the detailed solution. Let's say you have registered a repeating alarm with a pending intent like this:
Intent intent = new Intent("com.my.package.MY_UNIQUE_ACTION");
PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 0,
intent, PendingIntent.FLAG_UPDATE_CURRENT);
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis());
calendar.add(Calendar.MINUTE, 1);
AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), 1000 * 60, pendingIntent);
The way you would check to see if it is active is to:
boolean alarmUp = (PendingIntent.getBroadcast(context, 0,
new Intent("com.my.package.MY_UNIQUE_ACTION"),
PendingIntent.FLAG_NO_CREATE) != null);
if (alarmUp)
{
Log.d("myTag", "Alarm is already active");
}
The key here is the FLAG_NO_CREATE
which as described in the javadoc: if the described PendingIntent **does not** already exists, then simply return null
(instead of creating a new one)

- 820
- 4
- 18
- 33

- 24,333
- 24
- 88
- 134
-
9Does it have to use the Intent with just an Action String? I tried specifying a class, new Intent(context, MyClass.class) but it doesn't seem to work. It always returns null even when the alarm is running. – toc777 Apr 04 '12 at 08:39
-
5toc777, no it needs to be a String which matches a declared action in your intent-filter in your manifest.xml – Chris Knight Apr 11 '12 at 08:27
-
4Chris, It was another issue that was causing my problem. The intent I mentioned above actually does work :) – toc777 Apr 12 '12 at 12:25
-
An issue I had was not calling cancel on BOTH the alarmManager and the pendingIntent. I.E ~ alarmMgr.cancel(alarmIntent); alarmIntent.cancel(); – MobileMon May 29 '14 at 12:01
-
@ChrisKnight : Will this still work if I check from an app say app1 if an alarm is set and running in app2? and also,do the alarms die during an app update,and so do we need to reset it again(for app update case)? – Basher51 Jul 08 '14 at 03:25
-
1Always returns TRUE saying the pending intent already exist. Even after app uninstall and re-install. How long does the pending intent live? – Akh Aug 13 '14 at 20:33
-
50Note that you'll need to call both ```alarmManager.cancel(pendingIntent)``` and ```pendingIntent.cancel()``` in order for this solution to return false. – Kevin Cooper Sep 29 '14 at 20:00
-
1for users using new Intent(context, YourService.class) , you can use .setAction("ACTIONNAME") to define an action on the intent – Maxim Nov 28 '14 at 20:11
-
1Lifesaver. Please note that you'll need to create the intent exactly the same way you created it before, except for the flags. – Binoy Babu Feb 26 '15 at 10:07
-
30It case it isn't obvious, the code in this answer does not verify that the pending intent has been registered with the alarm manager. The code simply verifies that the PendingIntent was created via getBroadcast with an equivalent target intent. You can prove this by running the alarmUp code after the getBroadcast all, but before all the calendar and alarm manager stuff. It will return true. This fact explains why you have to PendingIntent.cancel to get the value to go back to false. Strictly speaking, this doesn't answer the question. – bigh_29 Apr 21 '15 at 21:09
-
2Excuse me. I want to ask what is MY_UNIQUE_ACTION ? Where it is coming from ? – Leonard Febrianto Jul 23 '15 at 01:14
-
1@LeonardFebrianto i think it was an answer long overdue but i am pretty sure you got the reason. Thats just the action name , it can be any action constant you have associated with receivers in your manifest – borax12 Dec 15 '15 at 05:49
-
does not work if alarm killed by 'force stop' etc.. It must be canceled before using this code – Jemshit Dec 17 '15 at 13:55
-
3I tried Intent intent = new Intent(ctx, MyReceiver.class); instead of passing unique_action and it worked :) – Narendra Singh Dec 22 '15 at 11:24
-
1tip for future readers - Make sure you are not mistaking PendingIntent.getBroadcast(...) with PendingIntent.getService(...) - save yourself some trouble! :) – Bruno Carrier Apr 18 '16 at 04:33
-
7this is the first time I see so high rated WRONG answer. See comment by bigh_29. – alex Jan 03 '17 at 20:29
-
Just if somebody wasted a day of figuring out why this doesn't work,.... flags has to be same/match as when you created the pending intent, e.g. FLAG_IMMUTABLE. – ThinkDeep Jul 11 '22 at 10:01
For others who may need this, here's an answer.
Use adb shell dumpsys alarm
You can know the alarm has been set and when are they going to alarmed and interval. Also how many times this alarm has been invoked.

- 1,635
- 1
- 11
- 7
-
41Not really a programmatic answer to the OP, but a cool tip. Very good to know. – JustSomeGuy May 06 '15 at 17:38
-
3append a grep to filter the usually long list of alarms: `adb shell dumpsys alarm | grep
` Also works on new Windows Systems (I use Win10) – muetzenflo Aug 08 '16 at 10:51 -
4grep is executed on the mobile device, not your PC. So if grep works depends on the Android OS. Older phones don't come with grep. – Henning Mar 07 '17 at 13:15
-
Working example with receiver (the top answer was just with action).
//starting
AlarmManager alarmManager = (AlarmManager) getActivity().getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(getActivity(), MyReceiver.class);
intent.setAction(MyReceiver.ACTION_ALARM_RECEIVER);//my custom string action name
PendingIntent pendingIntent = PendingIntent.getBroadcast(getActivity(), 1001, intent, PendingIntent.FLAG_CANCEL_CURRENT);//used unique ID as 1001
alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, System.currentTimeMillis(), aroundInterval, pendingIntent);//first start will start asap
//and stopping
Intent intent = new Intent(getActivity(), MyReceiver.class);//the same as up
intent.setAction(MyReceiver.ACTION_ALARM_RECEIVER);//the same as up
PendingIntent pendingIntent = PendingIntent.getBroadcast(getActivity(), 1001, intent, PendingIntent.FLAG_CANCEL_CURRENT);//the same as up
alarmManager.cancel(pendingIntent);//important
pendingIntent.cancel();//important
//checking if alarm is working with pendingIntent
Intent intent = new Intent(getActivity(), MyReceiver.class);//the same as up
intent.setAction(MyReceiver.ACTION_ALARM_RECEIVER);//the same as up
boolean isWorking = (PendingIntent.getBroadcast(getActivity(), 1001, intent, PendingIntent.FLAG_NO_CREATE) != null);//just changed the flag
Log.d(TAG, "alarm is " + (isWorking ? "" : "not") + " working...");
It is worth to mention:
If the creating application later (process) re-retrieves the same kind of PendingIntent (same operation, same Intent's - action, data, categories, components, flags), it will receive a PendingIntent representing the same token if that is still valid, and can thus call cancel() to remove it.
In short, your PendingIntent should have the same features (operation and intent's structure) to take control over it.

- 11,996
- 12
- 87
- 136
-
3I'm not sure that this is sufficient. In the case where a PendingIntent is registered with the AlarmManager and then stopped by both cancel methods, 'isWorking' above will still be true. The PendingIntent seems to have not been removed from the AlarmManager, and will keep returning an instance. How do we then effectively know when alarms have been turned on/off? – johnDisplayClass Jun 10 '16 at 07:36
-
This actually worked perfectly. Things to note: the setAction() and the requestCode() need to be identical in all getBroadcast()'s and its worth uninstalling the app from your device. That caught me out. Thanks – johnDisplayClass Jun 11 '16 at 10:12
-
-
1Nice example but I wouldn't use 1001 as private request code there. Just 0 to make the example more obvious. – Chris Jul 09 '17 at 08:12
-
-
2Please refrain from using "top answer" etc.. Instead provide a link to the answer. Because answers can change positions on the page based on popularity. – Kathir Dec 30 '18 at 06:48
-
This is not working solution, if you re-run the app from android studio, the pending intent get cleared, but `isWorking` return true, I guess same may happen when you update the app – Pavel Poley Nov 04 '22 at 11:54
Note this quote from the docs for the set method of the Alarm Manager:
If there is already an alarm for this Intent scheduled (with the equality of two intents being defined by Intent.filterEquals), then it will be removed and replaced by this one.
If you know you want the alarm set, then you don't need to bother checking whether it already exists or not. Just create it every time your app boots. You will replace any past alarms with the same Intent
.
You need a different approach if you are trying to calculate how much time is remaining on a previously created alarm, or if you really need to know whether such alarm even exists. To answer those questions, consider saving shared pref data at the time you create the alarm. You could store the clock timestamp at the moment the alarm was set, the time that you expect the alarm to go off, and the repeat period (if you setup a repeating alarm).

- 2,529
- 26
- 22
-
4In my opinion this should be the accepted answer. Unless the OP has an special situation that justifies not restating the alarm – Jose_GD May 19 '16 at 16:11
-
In my case, I want to know if the alarm is already set and if so I don't want to create new one or reset the existing alarm. – Imran Aslam Jul 21 '17 at 14:00
-
3Superb answer. Why didn't the OP check this at all? There's nothing you need to do. – Vijay Kumar Kanta Oct 05 '18 at 02:56
-
3There are many loop holes in this solution, this may override previously created alarm time (lets say if the time needs to be specified like t+24) so every time the app is launched alarm time keeps moving forward a state which it could never gets trigger for many, so checking the alarm if its already exists is more reliable one – Naga Feb 28 '19 at 10:54
I have 2 alarms. I am using intent with extras instead of action to identify the events:
Intent i = new Intent(context, AppReciever.class);
i.putExtra("timer", "timer1");
the thing is that with diff extras the intent (and the alarm) wont be unique. So to able to identify which alarm is active or not, I had to define diff requestCode
-s:
boolean alarmUp = (PendingIntent.getBroadcast(context, MyApp.TIMER_1, i,
PendingIntent.FLAG_NO_CREATE) != null);
and here is how alarm was created:
public static final int TIMER_1 = 1;
public static final int TIMER_2 = 2;
PendingIntent pending = PendingIntent.getBroadcast(context, TIMER_1, i,
PendingIntent.FLAG_CANCEL_CURRENT);
setInexactRepeating(AlarmManager.RTC_WAKEUP,
cal.getTimeInMillis(), AlarmManager.INTERVAL_DAY, pending);
pending = PendingIntent.getBroadcast(context, TIMER_2, i,
PendingIntent.FLAG_CANCEL_CURRENT);
setInexactRepeating(AlarmManager.RTC_WAKEUP,
cal.getTimeInMillis(), AlarmManager.INTERVAL_DAY, pending);

- 3,359
- 1
- 29
- 40
-
Using the intent extras and this solution worked for me. Only one change is I am using service so I have changed it to `PendingIntent.getService` – Pankaj Aug 27 '16 at 10:07
Just found another solution, it seems to work for me
Intent myIntent = new Intent(MainActivity.this, MyReceiver.class);
boolean isWorking = (PendingIntent.getBroadcast(MainActivity.this, 0, myIntent, PendingIntent.FLAG_NO_CREATE) != null);
if (isWorking) {Log.d("alarm", "is working");} else {Log.d("alarm", "is not working");}
if(!isWorking) {
pendingIntent = PendingIntent.getBroadcast(MainActivity.this, 0, myIntent, PendingIntent.FLAG_UPDATE_CURRENT);
alarmManager = (AlarmManager) getSystemService(ALARM_SERVICE);
int timeNotif = 5 * 60 * 1000;//time in ms, 7*24*60*60*1000 for 1 week
Log.d("Notif", "Notification every (ms): " + timeNotif);
alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), timeNotif, pendingIntent);
}

- 273
- 4
- 8
-
1Sometimes, on Marshmallow, after you force-stop an app, getBroadcast() will return non-null, but the alarm is not set. – hopia Feb 15 '18 at 20:14
-
While almost everyone over here has given the correct answer, no body explained on what basis are the Alarms work
You can actually learn more about AlarmManager
and its working here . But here is the quick answer
You see AlarmManager
basically schedules a PendingIntent
at some time in future. So in order to cancel the scheduled Alarm you need to cancel the PendingIntent
.
Always keep note of two things while creating the PendingIntent
PendingIntent.getBroadcast(context,REQUEST_CODE,intent, PendingIntent.FLAG_UPDATE_CURRENT);
- Request Code - Acts as the unique identifier
- Flag - Defines the behavior of
PendingIntent
Now to check if the Alarm is already scheduled or to cancel the Alarm you just need to get access to the same PendingIntent
. This can be done if you use same request code and use FLAG_NO_CREATE
like shown below
PendingIntent pendingIntent=PendingIntent.getBroadcast(this,REQUEST_CODE,intent,PendingIntent.FLAG_NO_CREATE);
if (pendingIntent!=null)
alarmManager.cancel(pendingIntent);
With FLAG_NO_CREATE
it will return null
if the PendingIntent
doesn't already exist. If it already exists it returns reference to the existing PendingIntent

- 8,346
- 16
- 39
- 53

- 1,243
- 11
- 10
-
1If Request Code is an identifier, is it important to pass the Intent with the matching Action? – Sekula1991 Apr 11 '19 at 12:54
-
Is there a way to get the time the alarm was scheduled for with the alarmanager if you have the pending intent? – M. Smith Feb 19 '20 at 18:15
I made a simple (stupid or not) bash script, that extracts the longs from the adb shell, converts them to timestamps and shows it in red.
echo "Please set a search filter"
read search
adb shell dumpsys alarm | grep $search | (while read i; do echo $i; _DT=$(echo $i | grep -Eo 'when\s+([0-9]{10})' | tr -d '[[:alpha:][:space:]]'); if [ $_DT ]; then echo -e "\e[31m$(date -d @$_DT)\e[0m"; fi; done;)
try it ;)

- 101
- 1
- 2
If you target Android 12 (i.e) Target SDK 31, then, for AlarmManager
, PendingIntent
cannot be created without a Mutable or an Immutable flag. Without this Mutability flag, the application will throw a runtime error. See this documentation for more details about this. The following code snippet is working for me and will help fellow people who target their application for Android 12.
For creating an Alarm:
public static void setupReminderServiceAlarm ( Context context ) {
Log.d ( TAG, "Trying to setup reminder service alarm" );
if (!isReminderServiceAlarmSet ( context )) {
AlarmManager alarmManager = (AlarmManager) context.getApplicationContext ().getSystemService ( Context.ALARM_SERVICE );
Intent intent = new Intent ( context.getApplicationContext (), ReminderIntentReceiver.class );
intent.setAction ( REMINDER_INTENT_ACTION );
PendingIntent pendingIntent;
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.S) {
pendingIntent = PendingIntent.getBroadcast ( context.getApplicationContext (), REMINDER_INTENT_REQUEST_CODE, intent, PendingIntent.FLAG_IMMUTABLE );
} else {
pendingIntent = PendingIntent.getBroadcast ( context.getApplicationContext (), REMINDER_INTENT_REQUEST_CODE, intent, 0 );
}
alarmManager.setRepeating ( AlarmManager.RTC_WAKEUP, getReminderTriggerTime (), REMINDER_INTERVAL, pendingIntent );
Log.d ( TAG, "Reminder service alarm setup completed" );
}
}
For checking whether the alarm is already set or not:
private static boolean isReminderServiceAlarmSet ( Context context ) {
Intent intent = new Intent ( context.getApplicationContext (), ReminderIntentReceiver.class );
intent.setAction ( REMINDER_INTENT_ACTION );
boolean isBackupServiceAlarmSet;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
PendingIntent.getBroadcast ( context.getApplicationContext (), REMINDER_INTENT_REQUEST_CODE, intent, PendingIntent.FLAG_IMMUTABLE | PendingIntent.FLAG_NO_CREATE );
isBackupServiceAlarmSet = (PendingIntent.getBroadcast ( context.getApplicationContext (), REMINDER_INTENT_REQUEST_CODE, intent, PendingIntent.FLAG_IMMUTABLE | PendingIntent.FLAG_NO_CREATE ) != null);
} else {
PendingIntent.getBroadcast ( context.getApplicationContext (), REMINDER_INTENT_REQUEST_CODE, intent, PendingIntent.FLAG_NO_CREATE );
isBackupServiceAlarmSet = (PendingIntent.getBroadcast ( context.getApplicationContext (), REMINDER_INTENT_REQUEST_CODE, intent, PendingIntent.FLAG_NO_CREATE ) != null);
}
Log.d ( TAG, "Reminder service alarm is " + (isBackupServiceAlarmSet ? "" : "not ") + "set already" );
return isBackupServiceAlarmSet;
}
For cancelling the alarm which was set earlier:
public static void cancelReminderServiceAlarm ( Context context ) {
Log.d ( TAG, "Reminder service alarm canceled" );
AlarmManager alarmManager = (AlarmManager) context.getApplicationContext ().getSystemService ( Context.ALARM_SERVICE );
Intent intent = new Intent ( context.getApplicationContext (), ReminderIntentReceiver.class );
intent.setAction ( REMINDER_INTENT_ACTION );
PendingIntent pendingIntent;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
pendingIntent = PendingIntent.getBroadcast ( context.getApplicationContext (), REMINDER_INTENT_REQUEST_CODE, intent, PendingIntent.FLAG_IMMUTABLE );
} else {
pendingIntent = PendingIntent.getBroadcast ( context.getApplicationContext (), REMINDER_INTENT_REQUEST_CODE, intent, 0 );
}
alarmManager.cancel ( pendingIntent );
pendingIntent.cancel ();
}
Hope this answer helps people who target their application for Android 12 / SDK 31+. Also, make sure to add this permission in Manifest for scheduling alarms targeting the above.
<uses-permission android:name="android.permission.SCHEDULE_EXACT_ALARM"/>

- 719
- 8
- 16
Intent intent = new Intent("com.my.package.MY_UNIQUE_ACTION");
PendingIntent pendingIntent = PendingIntent.getBroadcast(
sqlitewraper.context, 0, intent,
PendingIntent.FLAG_NO_CREATE);
FLAG_NO_CREATE is not create pending intent so that it gives boolean value false.
boolean alarmUp = (PendingIntent.getBroadcast(sqlitewraper.context, 0,
new Intent("com.my.package.MY_UNIQUE_ACTION"),
PendingIntent.FLAG_NO_CREATE) != null);
if (alarmUp) {
System.out.print("k");
}
AlarmManager alarmManager = (AlarmManager) sqlitewraper.context
.getSystemService(Context.ALARM_SERVICE);
alarmManager.setRepeating(AlarmManager.RTC_WAKEUP,
System.currentTimeMillis(), 1000 * 60, pendingIntent);
After the AlarmManager check the value of Pending Intent it gives true because AlarmManager Update The Flag of Pending Intent.
boolean alarmUp1 = (PendingIntent.getBroadcast(sqlitewraper.context, 0,
new Intent("com.my.package.MY_UNIQUE_ACTION"),
PendingIntent.FLAG_UPDATE_CURRENT) != null);
if (alarmUp1) {
System.out.print("k");
}

- 1,101
- 11
- 29
Based on my experience, in a more recent version of Android, I believe it only allows Broadcast messages for Alarm wake up, not starting services directly. See this link: https://developer.android.com/training/scheduling/alarms, it says:
Alarms have these characteristics:
- They let you fire Intents at set times and/or intervals.
- You can use them in conjunction with broadcast receivers to start services and perform other operations.
The operative word in the second sentence is "conjunction." What it explicitly states is that alarms are design for Broadcast (which implies not for starting services directly). I tried for several hours to use a PendingIntent with getService(), but could not get it to work, even though I confirmed the pending intent was working correctly simply using:
pendingIntent.send(0);
For "targetSdkVersion 29" this did not work .. [would not fire onStartCommand()]:
Intent launchIntent = new Intent(context, MyService.class);
launchIntent.putExtra(Type.KEY, SERVER_QUERY);
PendingIntent pendingIntent =
PendingIntent.getService(context, 0, launchIntent, 0);
I could validate the alarm was running using:
adb shell dumpsys alarm | grep com.myapp
However, this did work:
public static class AlarmReceiverWakeup extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
Log.i(TAG, "onReceive Alarm wakeup");
startService(context);
}
}
public static void scheduleAlarmWakeup(Context context) {
Intent broadcastIntent = new Intent(context, AlarmReceiverWakeup.class);
broadcastIntent.putExtra(Type.KEY, SERVER_QUERY);
PendingIntent pendingIntent =
PendingIntent.getBroadcast(context, 0, broadcastIntent, 0);
AlarmManager alarmManager =
(AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
// NOTE: using System.currentTimeMillis() fails w/ELAPSED_REALTIME_WAKEUP
// use SystemClock.elapsedRealtime() instead
alarmManager.setRepeating(
AlarmManager.ELAPSED_REALTIME_WAKEUP,
SystemClock.elapsedRealtime()+5000,
AlarmManager.INTERVAL_FIFTEEN_MINUTES/4,
getAlarmPendingIntent(context)
);
}
BTW, this is the AndroidManifest.xml entry for the Broadcast Receiver:
<receiver android:name=".ServerQueryService$AlarmReceiverWakeup"
android:enabled="true">
<intent-filter>
<category android:name="android.intent.category.DEFAULT"/>
</intent-filter>
</receiver>

- 351
- 2
- 7
Im under the impression that theres no way to do this, it would be nice though.
You can achieve a similar result by having a Alarm_last_set_time recorded somewhere, and having a On_boot_starter BroadcastReciever:BOOT_COMPLETED kinda thing.

- 29
- 6
I made a workaround with using the android jetpack workManager.
Instead of setting an alarm straight away in alarmManager, set work in workManager where you can set the trigger time (set trigger time in workManager) and add a tag to that work. The alarm can be set and triggered when the work triggers.
And to answer your question, you simply add tag to the work by .addTag("something")
and then when checking for an active work use .getWorkInfosByTag("something")

- 165
- 2
- 16