You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在BroadcastReceiver中实现WorkManager以避免ANR?

用WorkManager替代BroadcastReceiver处理耗时任务的实现方案

1. 添加WorkManager依赖

在app模块的build.gradle(或build.gradle.kts)中添加WorkManager的稳定版依赖:

dependencies {
    implementation "androidx.work:work-runtime:2.8.1"
}

2. 创建自定义Worker类

将原onReceive()中的耗时逻辑迁移至自定义Worker,WorkManager会自动在后台线程执行该任务:

class MyTaskWorker(context: Context, params: WorkerParameters) : Worker(context, params) {
    override fun doWork(): Result {
        // 此处放置原onReceive()中的耗时代码
        // 例:网络请求、本地文件读写、数据处理等

        return try {
            // 任务执行成功
            Result.success()
        } catch (e: Exception) {
            // 任务失败时,可选择重试或标记失败
            Result.retry()
            // 或 Result.failure()
        }
    }
}

如果使用Java实现:

public class MyTaskWorker extends Worker {
    public MyTaskWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
        super(context, workerParams);
    }

    @NonNull
    @Override
    public Result doWork() {
        // 耗时逻辑写在这里
        try {
            // 执行任务
            return Result.success();
        } catch (Exception e) {
            return Result.retry();
        }
    }
}

3. 修改BroadcastReceiver的onReceive方法

移除原广播接收器中的耗时代码,改为直接触发WorkManager执行任务:

class MyBroadcastReceiver : BroadcastReceiver() {
    override fun onReceive(context: Context?, intent: Intent?) {
        context ?: return
        
        // 构建一次性任务请求,提交后立即执行
        val workRequest = OneTimeWorkRequestBuilder<MyTaskWorker>()
            // 可选:传递参数给Worker
            // .setInputData(workDataOf("PARAM_KEY" to "PARAM_VALUE"))
            .build()
        
        // 提交任务到WorkManager
        WorkManager.getInstance(context).enqueue(workRequest)
    }
}

Java版本实现:

public class MyBroadcastReceiver extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {
        if (context == null) return;
        
        OneTimeWorkRequest workRequest = new OneTimeWorkRequest.Builder(MyTaskWorker.class)
                // 可选:传递参数
                // .setInputData(new Data.Builder().putString("PARAM_KEY", "PARAM_VALUE").build())
                .build();
        
        WorkManager.getInstance(context).enqueue(workRequest);
    }
}

4. 关键注意点

  • doWork()方法运行在WorkManager的后台线程,无需手动处理异步逻辑;
  • 若需传递数据,可通过InputData实现,Worker中通过inputData字段获取;
  • 可通过WorkManager.getWorkInfoByIdLiveData()监听任务执行状态,用于后续UI更新或结果处理;
  • 即使应用被后台回收,WorkManager会根据系统调度自动重启任务,保障任务完成。

内容的提问来源于stack exchange,提问作者Alessandro

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.15 04:25:17