java - androidx中的定期工作者
问题描述
androidx.work.Worker 仅在应用程序运行时工作。如果应用程序终止,PeriodicWorkRequest 将停止执行定期启动。
有必要在某个时间间隔显示通知,我使用 PeriodicWorkRequest,当应用程序正在运行(甚至最小化)时,它可以正常工作,当进程终止时没有更多通知。
工人阶级
import androidx.work.ExistingPeriodicWorkPolicy;
import androidx.work.Operation;
import androidx.work.PeriodicWorkRequest;
import androidx.work.WorkManager;
import androidx.work.WorkerParameters;
import java.util.concurrent.TimeUnit;
public class Worker extends androidx.work.Worker {
public static final String NOTIFICATION_TAG = "Notification";
public Worker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
super(context, workerParams);
Log.d(TAG, "NotificationWorkerInit");
}
@NonNull
@Override
public Result doWork() {
Log.d(TAG, "doWork: START");
Notification.showNotification(getApplicationContext());
return Result.success();
}
public static void doNotifications(Context context, int quantityPerDay) {
if (quantityPerDay > 0) {
startNotifications(context, quantityPerDay);
} else {
stopNotifications(context);
}
}
private static void startNotifications(Context context, int interval) {
int minInterval = 1;
PeriodicWorkRequest notificationsWorker = new PeriodicWorkRequest
.Builder(Worker.class, interval, TimeUnit.SECONDS, minInterval, TimeUnit.SECONDS)
.addTag(NOTIFICATION_TAG)
.build();
Log.d(TAG, "startNotificationsService: tag " + notificationsWorker.getTags());
Log.d(TAG, "startNotificationsService: id " + notificationsWorker.getId());
WorkManager workManager = WorkManager.getInstance(context);
Operation enqueue = workManager.enqueueUniquePeriodicWork(NOTIFICATION_TAG,
ExistingPeriodicWorkPolicy.REPLACE, notificationsWorker);
}
private static void stopNotifications(Context context) {
WorkManager.getInstance(context).cancelAllWorkByTag(NOTIFICATION_TAG);
Log.d(TAG, "stopNotifications: ");
}
}
依赖 build.gradle (app)
dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
implementation 'androidx.appcompat:appcompat:1.2.0'
implementation 'androidx.constraintlayout:constraintlayout:1.1.3'
implementation 'androidx.recyclerview:recyclerview:1.1.0'
// implementation 'org.jetbrains:annotations-java5:15.0'
implementation 'androidx.work:work-runtime:2.4.0'
implementation 'com.github.judemanutd:autostarter:1.0.8'
testImplementation 'junit:junit:4.13'
androidTestImplementation 'androidx.test.ext:junit:1.1.1'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.2.0'
}
清单许可(服务,接收者编号)
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.WAKE_LOCK"/>
日志中没有错误,这是关闭应用程序时写入的内容:
2020-08-09 18:28:31.772 1940-2694/system_process I/ActivityManager: Killing 5972:ego.emy.test/u0a85 (adj 900): remove task
2020-08-09 18:28:31.846 1940-2031/system_process W/InputDispatcher: channel 'e5ad803 ego.emy.test/ego.emy.test.MainActivity (server)' ~ Consumer closed input channel or an error occurred. events=0x9
2020-08-09 18:28:31.846 1940-2031/system_process E/InputDispatcher: channel 'e5ad803 ego.emy.test/ego.emy.test.MainActivity (server)' ~ Channel is unrecoverably broken and will be disposed!
2020-08-09 18:28:31.851 1940-4150/system_process I/WindowManager: WIN DEATH: Window{e5ad803 u0 ego.emy.test/ego.emy.test.MainActivity}
2020-08-09 18:28:31.851 1940-4150/system_process W/InputDispatcher: Attempted to unregister already unregistered input channel 'e5ad803 ego.emy.test/ego.emy.test.MainActivity (server)'
2020-08-09 18:28:31.856 1795-2041/? W/SurfaceFlinger: Attempting to destroy on removed layer: AppWindowToken{4ba78aa token=Token{5a74f95 ActivityRecord{634d34c u0 ego.emy.test/.MainActivity t9}}}#0
2020-08-09 18:28:32.285 1940-2261/system_process I/ActivityManager: Force stopping ego.emy.test appid=10085 user=0: from pid 6295
以前,类似的任务在升级到 androidx 问题开始后工作
解决方案
Well this what I found on official documentation -
WorkManager is an API that makes it easy to schedule deferrable, asynchronous tasks that are expected to run even if the app exits or the device restarts.
I believe your PeriodicWorkRequest is not working for you because you are creating PeriodicWorkRequest with incorrect time interval.
Note: The minimum repeat interval that can be defined is 15 minutes (more info)
PeriodicWorkRequest notificationsWorker = new PeriodicWorkRequest
.Builder(Worker.class, interval, TimeUnit.HOURS)
.addTag(NOTIFICATION_TAG)
.build();
Will repeat work in every 1 hours.
Similary periodic work that can run during the last 15 minutes of every one hour period.
PeriodicWorkRequest periodicWorkRequest =
new PeriodicWorkRequest.Builder(Worker.class,
1, TimeUnit.HOURS,
15, TimeUnit.MINUTES)
.build();
Happy Coding !
推荐阅读
- javascript - 确定我的自定义应用程序是否通过移动浏览器安装在设备上
- lua - Lua io.write() 不工作
- c# - C# linq 到 sql。Concat 与订单
- c# - SQLite.CodeFirst "提供者没有返回 ProviderManifest 实例。"
- kubernetes - Openshift - 重命名路线
- sql - SQL ORACLE 使用 htf(超文本函数)创建边框
- python-3.x - 停止轴扩展 matplotlib
- angular - 必须指定路由或分析模块中的错误
- python - 在 python 中的多个文件中使用变量(如 extern)而不分配变量而不是使用输入变量(不使用文件)
- cordova - 为什么 ionic-native/contacts 插件在尝试在 android 8 上保存联系人时会导致应用崩溃?