在广播接收器上运行Coroutine函数



我正在制作一个报警应用程序,并使用AlarmManager设置报警。在AlarmManager上运行setAlarm后,我会使用Room保存每个警报,这样,如果手机关机,我以后可以恢复它们。

我在设备启动后运行BroadcastReceiver,使用Android开发人员网站上的指南:https://developer.android.com/training/scheduling/alarms#boot

我的想法是通过onReceive方法从Room获取警报但是Room使用了一个暂停的乐趣来获得警报,但我不能在onReceive上运行它,因为BroadcastReceiver没有生命周期

我怎样才能取得类似的结果?

BroadcastReceiver文档中的这一节给出了如何做到这一点的示例。

你可以用一个扩展功能来清理一下:

fun BroadcastReceiver.goAsync(
context: CoroutineContext = EmptyCoroutineContext,
block: suspend CoroutineScope.() -> Unit
) {
val pendingResult = goAsync()
@OptIn(DelicateCoroutinesApi::class) // Must run globally; there's no teardown callback.
GlobalScope.launch(context) {
try {
block()
} finally {
pendingResult.finish()
}
}
}

然后在你的接收器中,你可以像下面这样使用它。goAsync块中的代码是一个协程。请记住,您不应该在这个协程中使用Dispatchers.Main,它必须在10秒内完成。

override fun onReceive(context: Context, intent: Intent) = goAsync {
val repo = MyRepository.getInstance(context)
val alarms = repo.getAlarms() // a suspend function
// do stuff
}

你可以这样做:

override fun onReceive(context: Context, intent: Intent)  {
if (intent.action == "android.intent.action.BOOT_COMPLETED") {
CoroutineScope(Dispatchers.IO).launch {
try {
// you code here

} finally {
cancel()
}
}
}
}

最新更新