我最近将我的所有服务替换为前台服务和 JobIntentService,因为在 oreo 及更高版本中存在一些后台执行限制(https://developer.android.com/about/versions/oreo/background)。根据文档,JobIntentService 的作用类似于 Android 7 及更低版本的 Intent Service,并且类似于 Android 8 及更高版本的 JobScheduler。我注意到 Google 提供的新 JobIntentService 存在问题。
安卓8及以上:
在 android 8 及更高版本中不断发生崩溃。这里提出了一张票,提到了同样的问题https://issuetracker.google.com/issues/63622293,我添加了一些极客建议的临时修复。
Android 7 及更低版本: 工作完成后,其行为类似于 Intent Service 的 JobIntentService 不会停止。
我已经在服务中实现了 JobIntentService,只要用户执行某些操作就会触发。
代码
public class SampleJobIntentService extends FixedJobIntentService {
public static void postData(Context context, String data) {
Intent intent = new Intent(context, SampleJobIntentService.class);
intent.setAction(INITIAL_ACTION);
intent.putExtra(SAMPLE_ID, data);
SampleJobIntentService.enqueueWork(context,intent);
}
public static void enqueueWork(Context context, Intent work) {
SampleJobIntentService.enqueueWork(context, SampleJobIntentService.class, JOB_ID, work);
@Override
protected void onHandleWork(@NonNull Intent intent) {
if (intent != null) {
SampleRequest sampleRequest = requests.get(intent.getAction());
if (sampleRequest != null) {
try {
// perform some networking operations
} catch (Exception ex) {
Log.d("Error for intent ");
}
Log.i("send action ");
} else
Log.e("action not found for ");
}
}
}
为了避免 JobIntentService 崩溃,我从https://issuetracker.google.com/issues/63622293中引用了一些参考资料
public abstract class FixedJobIntentService extends JobIntentService {
@Override
GenericWorkItem dequeueWork() {
try {
return new FixedGenericWorkItem(super.dequeueWork());
} catch (SecurityException ignored) {
doStopCurrentWork();
}
return null;
}
private class FixedGenericWorkItem implements GenericWorkItem {
final GenericWorkItem mGenericWorkItem;
FixedGenericWorkItem(GenericWorkItem genericWorkItem) {
mGenericWorkItem = genericWorkItem;
}
@Override
public Intent getIntent() {
if (mGenericWorkItem != null) {
return mGenericWorkItem.getIntent();
}
return null;
}
@Override
public void complete() {
try {
if (mGenericWorkItem != null) {
mGenericWorkItem.complete();
}
} catch (IllegalArgumentException ignored) {
doStopCurrentWork();
}
}
}
}