在Android上运行长时间服务的最佳架构

17
我希望能得到一些关于如何处理操作系统终止长时间运行服务的指导。
业务场景:
应用程序会记录BTT轨迹,该轨迹可能持续几个小时。它还可以在地图上显示轨迹以及相关统计信息。
应用程序用户界面允许用户开始/停止轨迹记录并在地图上实时查看轨迹。
开始轨迹记录后,用户可以退出应用程序并关闭屏幕(以节省电力),只有一个服务继续运行,以便将记录更新到数据库(显示通知),直到用户再次启动活动并要求停止录音,这将导致服务终止。
问题:
经过可变时间,从40分钟到1个半小时不等,录制服务会在没有任何警告的情况下被终止。由于BTT出游可能需要数小时,因此导致轨迹记录不完整。
一些额外的信息:
服务使用START_STICKY启动并获取PARTIAL_WAKE_LOCK,并在与主活动相同的进程中运行。
新位置按用户定义的速率从每秒到几分钟进行获取(并记录)。
我了解从Android文档中得知这是长时间运行服务的预期操作系统行为。
问题:
什么是最好的架构设计方法,以满足业务场景要求的良好应用程序?
我能想到几个选项(我都不喜欢),但我希望从已经面临并解决类似问题的人那里得到指导:
使用广播接收器(最好连接到Location Manager,如果可能的话),当获取新位置时才运行服务?
不允许用户离开主要活动(导致用户体验差)?
有一个闹钟广播接收器在需要时重新启动服务?
感谢所有能在这个问题上分享智慧的人。
1个回答

9

我有一个应用程序,它做的事情非常相似。我通过将其设置为前台任务来确保服务持续运行。当我准备好开始运行时,我调用这个函数,它还设置了一个通知:

void fg() {
    Notification notification = new Notification(R.drawable.logstatus, 
                    "Logging On", System.currentTimeMillis());
    Intent notificationIntent = new Intent(this, LoggerActivity.class);
    PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, 
                    notificationIntent, 0);
    notification.setLatestEventInfo(this, "Logger","Logger Running",
                pendingIntent);
    startForeground(1, notification);   
}

当日志记录完成后,需要离开前台模式:

stopForeground(true);

谢谢Michael。我会测试它并告诉你结果。 - Luis
它已经运行了数小时而没有停止。问题已解决 :-) 再次感谢 Michael。 - Luis
我的项目中无法解决notification.setLatestEventInfo(.....)方法。有什么解决方案吗? - Himanshu Mori
1
@HimanshuMori setLatestEventInfo在API级别23(Android M)中已被移除。你可以选择编译一个旧版本的API,或者使用新的NotificationCompat.Builder。详细例子请查看 https://dev59.com/5FwY5IYBdhLWcg3wq5Xk, https://dev59.com/5mQn5IYBdhLWcg3wamjO, https://stackoverflow.com/questions/34012544/alternative-way-on-how-to-change-setlatesteventinfo-in-notification-receiver - Michael
谢谢 @Michael,将服务启动在前台模式下对我帮助很大。 - Himanshu Mori

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接