【问题标题】:Service in Oreo奥利奥的服务
【发布时间】:2018-09-26 19:00:20
【问题描述】:

我正在开发一个应用程序(minSDK = 19 & targetSDK = 26),其中有 20 个服务,例如MediaPlayer、SyncUpData 和 SyncDownData 等服务。因为 Android O 不允许长时间运行后台服务。我很困惑在 JobScheduler、FirebaseJobDispature、JobIntentService 等之间选择什么,因为 API 21 中引入了 JobShecduler,API 14 中引入了 FirebaseJobDispature。

另一个问题是如何检查哪些服务需要替换为上述框架,哪些不需要。

即使应用程序不可见,也有 3 个服务应该运行,因为这些服务向/从蓝牙设备发送/接收数据包。它们将在应用程序终止或手动断开连接时停止运行。

我知道网上有很多解决方案,但我很困惑我应该使用哪个。

请为此提出合适的解决方案。 TIA

【问题讨论】:

    标签: android android-service android-8.0-oreo


    【解决方案1】:

    最好使用的是新的WorkManager 库。 它包含了所有可能的 API 级别场景:

    • 为 API 23+ 使用 JobScheduler
    • 对于 API 14-22 如果在应用中使用 Firebase JobDispatcher 和可选的 Firebase 依赖项,请使用 Firebase JobDispatcher
    • 否则,使用自定义的AlarmManager + 广播接收器实现

    另外,here一些文献和使用例子。

    WorkManager 用例仅适用于需要保证执行的后台作业,即使在应用程序被终止后也是如此。

    如果您需要前台服务,那么只需通过扩展Service 类自行创建即可。对于 Oreo,您需要显示 UI 通知。然后可以在下一次调用时将服务作为前台启动:

    ContextCompat.startForegroundService(context, yourService);
    

    虽然如果服务仅在应用处于活动状态时存在,并且通过应用手动停止或在应用存在时停止,那么您应该考虑使用线程而不是服务。

    Quote 来自 android 文档:

    如果您需要在主线程之外执行工作,但仅在用户与您的应用程序交互时执行,那么您可能应该创建一个新线程而不是服务。例如,如果您想播放一些音乐,但仅在您的活动运行时,您可以在 onCreate() 中创建一个线程,在 onStart() 中开始运行它,然后在 onStop() 中停止它。还可以考虑使用 AsyncTask 或 HandlerThread,而不是传统的 Thread 类。有关线程的更多信息,请参阅进程和线程文档。

    请记住,如果您确实使用服务,默认情况下它仍会在应用程序的主线程中运行,因此如果它执行密集或阻塞操作,您仍应在该服务中创建一个新线程。

    【讨论】:

    • 我刚刚在 android O 上运行了应用程序,没有进行任何更改,它工作正常。 onStartService() 正在工作。有什么想法吗??
    • 你能澄清一下吗?你的意思是正如你所写的那样有效?你没想到它会起作用?或者是一个错字,你的意思是不工作?
    • 我没有对您建议的与 WorkManager 或其他任何内容相关的任何更改进行任何更改,但该服务仍在 Oreo 设备上运行。
    • 你的问题是关于选择什么Service,答案是WorkManager。这是所有服务的包装器。有了它,您无需担心要使用哪个服务,如 JobShecduler、JobIntentService 或任何其他服务等。您也无需担心是否有任何服务被弃用。 WorkManager 作为包装器是所有这些的完美替代品。在内部,它会根据当前 API 级别选择最佳服务。当然,您仍然可以使用您想要的任何服务,并且它可能会起作用,但是您需要考虑它是否会被弃用,或者它是否适用于所有 API 级别。
    • 如何确定哪个服务将作为前台或后台服务工作??