From f7a1ba684af536c89095e2b60c827b39417df52c Mon Sep 17 00:00:00 2001
From: Wouter Willems <ww@qbus.be>
Date: Mon, 19 Feb 2024 14:51:07 +0100
Subject: [PATCH 1/4] fix for exact allarms not allowed

---
 serviceLibrary/src/main/AndroidManifest.xml       |  2 +-
 .../mqtt/android/service/ping/AlarmPingSender.kt  | 15 ++++++++++++++-
 2 files changed, 15 insertions(+), 2 deletions(-)

diff --git a/serviceLibrary/src/main/AndroidManifest.xml b/serviceLibrary/src/main/AndroidManifest.xml
index 46730d81..1e7cb8d9 100755
--- a/serviceLibrary/src/main/AndroidManifest.xml
+++ b/serviceLibrary/src/main/AndroidManifest.xml
@@ -3,7 +3,7 @@
     <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
     <uses-permission android:name="android.permission.INTERNET" />
     <uses-permission android:name="android.permission.SCHEDULE_EXACT_ALARM" />
-    <uses-permission android:name="android.permission.USE_EXACT_ALARM" />
+    <!-- <uses-permission android:name="android.permission.USE_EXACT_ALARM" /> this is only required for calendar apps -->
     <uses-permission android:name="android.permission.WAKE_LOCK" />
     <uses-permission android:name="android.permission.FOREGROUND_SERVICE_DATA_SYNC" />
 
diff --git a/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt b/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
index b4d5e7e3..5f71a2fd 100755
--- a/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
+++ b/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
@@ -81,7 +81,20 @@ internal class AlarmPingSender(val service: MqttService) : MqttPingSender {
         Timber.d("Schedule next alarm at $nextAlarmInMilliseconds ms")
         val alarmManager = service.getSystemService(Service.ALARM_SERVICE) as AlarmManager
         pendingIntent?.let {
-            if (Build.VERSION.SDK_INT >= 23) {
+            //add check for android 13 and up
+            if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
+                //check if we can scheduele exact alarms
+                if(alarmManager.canScheduleExactAlarms()) {
+                    Timber.d("Alarm schedule using setExactAndAllowWhileIdle, next: $delayInMilliseconds")
+                    alarmManager.setExactAndAllowWhileIdle(AlarmManager.ELAPSED_REALTIME_WAKEUP, nextAlarmInMilliseconds, it)
+                } else // it's up to the app to ask for permission so we schedule with a no exact but we do warn in the logs about it
+                {
+                    Timber.w("Not allowed to schedule exact alarms! using non exact alarm")
+                    Timber.w("Alarm schedule using setExactAndAllowWhileIdle, next: $delayInMilliseconds")
+                    alarmManager.setAndAllowWhileIdle(AlarmManager.ELAPSED_REALTIME_WAKEUP, nextAlarmInMilliseconds, it)
+                }
+            }
+            else if (Build.VERSION.SDK_INT >= 23) {
                 // In SDK 23 and above, dosing will prevent setExact, setExactAndAllowWhileIdle will force
                 // the device to run this task whilst dosing.
                 Timber.d("Alarm schedule using setExactAndAllowWhileIdle, next: $delayInMilliseconds")

From e30812e7a4cdde0bc88df046893161eeb79f51f1 Mon Sep 17 00:00:00 2001
From: Wouter Willems <ww@qbus.be>
Date: Mon, 19 Feb 2024 15:02:11 +0100
Subject: [PATCH 2/4] comment fix

---
 .../main/java/info/mqtt/android/service/ping/AlarmPingSender.kt | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt b/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
index 5f71a2fd..b1531d0b 100755
--- a/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
+++ b/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
@@ -90,7 +90,7 @@ internal class AlarmPingSender(val service: MqttService) : MqttPingSender {
                 } else // it's up to the app to ask for permission so we schedule with a no exact but we do warn in the logs about it
                 {
                     Timber.w("Not allowed to schedule exact alarms! using non exact alarm")
-                    Timber.w("Alarm schedule using setExactAndAllowWhileIdle, next: $delayInMilliseconds")
+                    Timber.w("Alarm schedule using setAndAllowWhileIdle, next: $delayInMilliseconds")
                     alarmManager.setAndAllowWhileIdle(AlarmManager.ELAPSED_REALTIME_WAKEUP, nextAlarmInMilliseconds, it)
                 }
             }

From 36f94cd6989fcfdcfdc03fa12e7bbe008613c0f5 Mon Sep 17 00:00:00 2001
From: Wouter Willems <ww@qbus.be>
Date: Mon, 19 Feb 2024 15:16:51 +0100
Subject: [PATCH 3/4] formated code

---
 .../java/info/mqtt/android/service/ping/AlarmPingSender.kt | 7 +++----
 1 file changed, 3 insertions(+), 4 deletions(-)

diff --git a/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt b/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
index b1531d0b..e29a3aeb 100755
--- a/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
+++ b/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
@@ -82,9 +82,9 @@ internal class AlarmPingSender(val service: MqttService) : MqttPingSender {
         val alarmManager = service.getSystemService(Service.ALARM_SERVICE) as AlarmManager
         pendingIntent?.let {
             //add check for android 13 and up
-            if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
+            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
                 //check if we can scheduele exact alarms
-                if(alarmManager.canScheduleExactAlarms()) {
+                if (alarmManager.canScheduleExactAlarms()) {
                     Timber.d("Alarm schedule using setExactAndAllowWhileIdle, next: $delayInMilliseconds")
                     alarmManager.setExactAndAllowWhileIdle(AlarmManager.ELAPSED_REALTIME_WAKEUP, nextAlarmInMilliseconds, it)
                 } else // it's up to the app to ask for permission so we schedule with a no exact but we do warn in the logs about it
@@ -93,8 +93,7 @@ internal class AlarmPingSender(val service: MqttService) : MqttPingSender {
                     Timber.w("Alarm schedule using setAndAllowWhileIdle, next: $delayInMilliseconds")
                     alarmManager.setAndAllowWhileIdle(AlarmManager.ELAPSED_REALTIME_WAKEUP, nextAlarmInMilliseconds, it)
                 }
-            }
-            else if (Build.VERSION.SDK_INT >= 23) {
+            } else if (Build.VERSION.SDK_INT >= 23) {
                 // In SDK 23 and above, dosing will prevent setExact, setExactAndAllowWhileIdle will force
                 // the device to run this task whilst dosing.
                 Timber.d("Alarm schedule using setExactAndAllowWhileIdle, next: $delayInMilliseconds")

From fa3ac6eadfd8b3106cf9c741baefdf293f3c591f Mon Sep 17 00:00:00 2001
From: Wouter Willems <ww@qbus.be>
Date: Mon, 19 Feb 2024 16:03:57 +0100
Subject: [PATCH 4/4] there was a fall through in the else

---
 .../java/info/mqtt/android/service/ping/AlarmPingSender.kt   | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

diff --git a/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt b/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
index e29a3aeb..e350c837 100755
--- a/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
+++ b/serviceLibrary/src/main/java/info/mqtt/android/service/ping/AlarmPingSender.kt
@@ -98,9 +98,10 @@ internal class AlarmPingSender(val service: MqttService) : MqttPingSender {
                 // the device to run this task whilst dosing.
                 Timber.d("Alarm schedule using setExactAndAllowWhileIdle, next: $delayInMilliseconds")
                 alarmManager.setExactAndAllowWhileIdle(AlarmManager.ELAPSED_REALTIME_WAKEUP, nextAlarmInMilliseconds, it)
-            } else
+            } else {
                 Timber.d("Alarm schedule using setExact, delay: $delayInMilliseconds")
-            alarmManager.setExact(AlarmManager.ELAPSED_REALTIME_WAKEUP, nextAlarmInMilliseconds, it)
+                alarmManager.setExact(AlarmManager.ELAPSED_REALTIME_WAKEUP, nextAlarmInMilliseconds, it)
+            }
         }
     }