Martin BraunandJosé Rebelo b8a85e03ea Add Third Party Alarm Intent API: Set and Dismiss alarms for your device from any app (#6088)
Adds the capability to set and dismiss alarms from third party apps through an Intent API, fixes #5553

**This PR was co-authored by ChatGPT and José Rebelo (passively):**

- Scaffold for the core component `DeviceAlarmReceiver` was taken from José's `DeviceSettingsReceiver`
- The core implementation was written by me by hand, ChatGPT was used to review and find potential issues and bugs
- The `DeviceAlarmReceiverTest` unit tests were written by ChatGPT and reviewed by me

**About these changes:**

- Adds a new developer settings entry for the device that the user needs to enable, so other apps can use the Intent API for such device
- Supports app blacklisting as it is done in the `DeviceSettingsReceiver`
- `ConfigureAlarms.addMissingAlarms()` was migrated to `DBHelper.fillMissingAlarms()` to provide this abstraction globally
- `AlarmReceiver` was migrated to `SunriseSunsetAlarmReceiver` to avoid ambiguity with this feature; the formerly called `AlarmReceiver` was related to setting calendar events based on the sunrise/sunset via an Intent API
- The API is registered in the `DeviceCommunicationService`
- The `ConfigureAlarms` activity updates its list after setting alarms from a third party app by broadcasting `ACTION_SAVE_ALARMS`
- It is possible to set alarms of a device that is offline, it should sync when the device connects next time, unless it downloads the alarms from the device when connecting
- However, this device-to-GadgetBridge alarm sync API is not commonly abstracted, so we cannot respect existing alarms on the devices when changing alarms within the new Intent API; the database is the single source of truth and connecting the device after using the API will reset alarms
- ~~The API was designed to align with the `AlarmClock` API from Android, but~~ there is no feature parity to improve the design and interaction; after all the `AlarmClock` API is interacted with `startActivity`, but `GadgetBridge` uses `sendBroadcast` receivers, which is recommend for background tasks
- Errors are not raised to the caller (i.e. providing unknown or invalid Mac Address of device or trying to set an alarm on a nonexisting slot); these errors are logged though

**EDIT: Additional changes during the development:**

- Since slot IDs are unpredictable, the flow is title-driven (there is no way to provide an ID)
- Dismissing an alarm through the API removes its title
- Only alarms without a title can be overwritten and a title should be set through this API to retain the ability to dismiss it without dismissing all alarms of the user
- Dismissing all alarms regardless of the title is still possible
- The title is exposed in the UI not just when the device supports it, but also when this API is enabled in the developer settings of the device itself

**Example usage:**

- https://gitlab.com/martin-braun/warpclock-plus/-/blob/feat/gb/app/src/main/java/com/antonok/warpclock/AlarmIntentService.kt demonstrates dismissing all alarms and setting multiple alarms (search for `sendBroadcast`)
- `DeviceAlarmReceiverTest` should cover all cases for a more complete overview of the capabilities of the API

Reviewed-on: https://codeberg.org/Freeyourgadget/Gadgetbridge/pulls/6088
2026-05-21 19:57:07 +02:00
2026-04-14 23:32:15 +01:00
2026-05-17 09:13:29 +01:00
2026-05-14 21:12:43 +01:00
2025-07-06 21:16:45 +01:00
2026-05-19 23:53:38 +01:00
2025-12-04 21:27:21 +01:00
2026-01-03 09:56:03 +00:00
2026-05-11 22:36:36 +02:00
2026-05-11 22:36:36 +02:00
2017-11-01 14:58:43 +01:00

Gadgetbridge is hosted on codeberg.org.

Gadgetbridge

Gadgetbridge is an Android application which will allow you to use your Bluetooth gadgets (mostly wearables like smart watches, but many more) without the vendor's closed source application and without the need to create an account and transmit any of your data to the vendor's servers.

Homepage - Blog - Mastodon

Donate

Translate

Download

Get it on F-Droid Get it on IzzyOnDroid Get it on Codeberg

RB Status

  • Nightly releases
    • Nightly releases are updated more frequently and may be less stable than standard releases, and they are distributed by our F-Droid repository unlike standard releases.
  • List of changes

Supported Devices

Please see the Gadgets page on the website for a complete list of supported devices.

Features

Please see the Features page on the website.

Authors

Core Team (in order of first code contribution)

  • Andreas Shimokawa
  • Carsten Pfeiffer
  • Daniele Gobbetti
  • Petr Vaněk

Additional contributors

  • João Paulo Barraca (HPlus)
  • Vitaly Svyastyn (NO.1 F1)
  • Sami Alaoui (Teclast H30)
  • "ladbsoft" (XWatch)
  • Sebastian Kranz (ZeTime)
  • Vadim Kaushan (ID115)
  • "maxirnilian" (Lenovo Watch 9)
  • "ksiwczynski", "mkusnierz", "mamutcho" (Lenovo Watch X Plus)
  • Andreas Böhler (Casio)
  • Jean-François Greffier (Mi Scale 2)
  • Johannes Schmitt (BFH-16)
  • Lukas Schwichtenberg (Makibes HR3)
  • Daniel Dakhno (Fossil Q Hybrid, Fossil Hybrid HR)
  • Gordon Williams (Bangle.js)
  • Pavel Elagin (JYou Y5)
  • Taavi Eomäe (iTag)
  • Erik Bloß (TLW64)
  • Yukai Li (Lefun)
  • José Rebelo (Roidmi, Sony Headphones, Miband 7)
  • Arjan Schrijver (Fossil Hybrid HR watchfaces)

Contribute

Contributions are welcome, be it feedback, bug reports, documentation, translation, research or code. Feel free to work on any of the open issues; just leave a comment that you're working on one to avoid duplicated work.

Developer documentation - Support for a new Device - New Device Tutorial

Translations can be contributed via https://hosted.weblate.org/projects/freeyourgadget/gadgetbridge/

Community

If you would like to get in touch with other Gadgetbridge users and developers outside of Codeberg, you can do so via:

Do you have further questions or feedback?

Feel free to open an issue on our issue tracker, but please:

  • do not use the issue tracker as a forum, do not ask for ETAs and read the issue conversation before posting
  • use the search functionality to ensure that your question wasn't already answered. Don't forget to check the closed issues as well!
  • remember that this is a community project, people are contributing in their free time because they like doing so: don't take the fun away! Be kind and constructive.
  • Do not ask for help regarding your own projects, unless they are Gadgetbridge related

Having problems?

  1. Phone crashing during device discovery? Disable Privacy Guard (or similarly named functionality) during discovery.
  2. Open Gadgetbridge's settings and check the option to write log files
  3. Reproduce the problem you encountered
  4. Check the logfile at /sdcard/Android/data/nodomain.freeyourgadget.gadgetbridge/files/gadgetbridge.log
  5. File an issue at https://codeberg.org/Freeyourgadget/Gadgetbridge/issues/new/choose and possibly provide the logfile

Alternatively you may use the standard logcat functionality to access the log.

Code Licenses

  • Gadgetbridge is licensed under the AGPLv3
  • Files in app/src/main/java/net/osmand/ and app/src/main/aidl/net/osmand/ are taken from the OsmAnd project, licensed under the GPLv3 by OsmAnd BV
  • Files in app/src/main/java/org/bouncycastle are taken from the Bouncy Castle project, licensed under the MIT license by The Legion of the Bouncy Castle Inc.
  • Files in app/src/main/java/com/android/nQuant are taken from the nQuant.android project, licensed under the Apache license by Miller Cy Chan
  • Files in app/src/main/java/org/concentus are taken from the Concentus project, licensed under the BSD-3 license by various holding parties
  • Files in GBDaoGenerator/src/de/greenrobot are taken from the greenDAO project (Gadgetbridge's fork), licensed under the GPLv3 by Markus Junginger, greenrobot
  • File app/src/main/java/nodomain/freeyourgadget/gadgetbridge/util/SearchPreferenceHighlighter.java is taken from SearchPreference, licensed under the MIT license by ByteHamster
S
Description
No description provided
Readme AGPL-3.0
136 MiB
Languages
Java 91.8%
Kotlin 7.7%
FreeMarker 0.2%
Shell 0.1%