关于进程保活的两三事——新手升级经验卡

首先,先搁下几个问题,什么是进程保活?为什么要有进程保活?最后才是进程保活要怎么实现??相信大家会迫不及待跳到最后一个问题去看保活要怎么实现,可本文致力于为新手铺路,保驾护航。

一、什么是进程保活?

一开始接触到这个的时候,我是觉得太高大上了,android进程是什么东西,一个应用就是一个进程吗?NoNoNo,图样图森破,这是我刚毕业的时候还有的想法。之前的说android一个应用可以有多个进程,简称应用内多进程,当然,在这里没必要扩展,扩展的话就涉及到linux的知识了。那么到这里可能对于新手级(对这方面没有接触的朋友们)一切都还是懵逼的,其实简单点来说,我们打开手机的应用管理,就可以看到正在运行的应用有

关于进程保活的两三事——新手升级经验卡_第1张图片
经典"永生"程序QQ和微信

我们可以看到QQ跟微信明明我们只是打开了一次,但是却显示有多个进程跟服务,这里我们看到的就是进程保活了,通过一个进程来让应用服务常驻后台,即使用户不打开应用,也要背着用户搞小动作的猥琐行为,就是我们常说的进程保活了。而进程保活的最高境界就是实现在不同android系统上都能够永生不死。当然了,可能有大牛会说,别逗,不存在永生不死的进程,什么进程都可以kill掉,这里指的永生不死是用户接受范围内的常驻后台,如果用户真的很不开心,另辟蹊径也要杀掉进程,就别起来了,等到合适的契机再重启吧,不然会被定位为流氓软件的。

关于进程保活的两三事——新手升级经验卡_第2张图片
又装逼了...

二、为什么要有进程保活?

最近项目中加入了推送的功能,之前的推送都是基于定时器,轮询实现的,这个不用大家评论都只知道轮询肯定是耗费资源的,虽然我不知道具体会耗费多少的资源,会做多少的无用功,但用推送代替轮询,不管从哪方面考虑都是极好的。言归正传,先说一下最近对推送功能的感悟(吐槽一下国内用不了google的推送功能,感叹一下websocket全双工的微妙),一般来说,我们的应用都需要推送!!为什么呢?因为如果没有推送的话,那么一切的会话都变成从客户端发起的,因为http的局限,而我们大多数的应用都是基于http进行网络交互的,所以,推送就成了提高用户体验,为app与用户之间创造了更多交互机会的桥梁了。不得不说,这个功能是我入行以来做过最赞的功能!!难度可以说是最简单的,比登录注册还要简单...推送服务,就是一个我们需要保活的进程,不然用户杀掉APP,就没有推送功能了,老板肯定不干啊,而且用户本来的用意也不想接收推送啊,只是因为android的生态环境导致用户养成了不使用就直接从后台杀死应用的习惯。

关于进程保活的两三事——新手升级经验卡_第3张图片

虽然用户养成了这么坏的习惯,但是我们总不能在双击返回键退出的时候,再添加一个“为了推送功能不要从后台杀死应用”。所以,仅仅是为了正常的推送功能的实现,我们就应该让进程能够常驻后台,也就是说进程保活了。杀了能重启,杀了能重启...

三、如何实现进程保活呢?

前面洋洋洒洒的吹了几百字,终于到了重头戏了。怎么实现进程保活呢?相信android刚出道的时候,android开发者还是很淳朴的,并没有想要做流氓软件,骚扰用户这些破坏android生态环境的事。所以在网上有一大堆的实现所谓的进程保活的方法,由浅入深吧:

1、使用系统广播来唤醒app服务

相信大家在学习android的时候,都会有一本android基础的教科书,哈哈,想当年我决定做android的时候,只看了一下java基础就去面试腾讯的android实习岗位,也是蛮秀逗的啊。当然,面试没过...不过后来我仔细研究android基础的时候,就发现静态注册的广播接收器,也就是在AndroidManifest.xml文件里面配置的receiver,任何时候都能够接收广播进行处理,这样的话,就产生了方法1,我们可以借助系统广播来打开我们app的后台服务,比如

android.intent.action.ACTION_TIME_TICK

android.intent.action.USER_PRESENT

android.intent.action.PRE_BOOT_COMPLETED

...

如果你认为一切都是这样的简单,那就真的是图样图森破了,网上大多数的关于进程自启动,进程保活的资料都是使用的这个方法,当我们满心期待地想要实现这个“简单”的功能时,就会发现,教科书讲大话!广播接收器并没有接收到广播,说好的在清单文件中注册广播接收器就能够接受全局广播的呢?我也在这里纠结了很久,曾经一度沮丧说android的教科书太气人了,竟然蒙骗我这种新手。后来经过多番研究,发现在android3.1之后,使用了新的广播机制,该平台定义了两个新的Intent的Flag,让发送者指定的意图是否应该被允许激活停止的应用程序的组件。分别为

FLAG_INCLUDE_STOPPED_PACKAGES 包括停止的应用

FLAG_EXCLUDE_STOPPED_PACKAGES 不包括停止的应用

当两个Flag都不设置或都设置的时候,默认操作是FLAG_INCLUDE_STOPPED_PACKAGES。包含停止的应用。

而问题就出在这里了,android3.1之后,系统在构造系统广播的intent时,向所有的Intent的广播添加了FL​​AG_EXCLUDE_STOPPED_PACKAGES标志。它这样做的目的就是避免坏的android开发者利用系统广播瞒着用户做一些坏事,比如开启后台服务,要是每个应用都开启后台服务,并且在服务里面做一些联网,存取数据库的操作,那么最直观的就是我们的流量哗啦啦的就花光了。这个改动既是为了安全,也是为了维护android的生态环境。

但是后台服务或应用程序仍然可以通过向广播Intent添加FLAG_INCLUDE_STOPPED_PACKAGES标志来唤醒处于停止状态(stopped state)的应用程序。由此就引出了一种切实可行的实现进程保活的方法,利用第三方应用来唤醒本应用

应用程序处于停止状态有两种情况,一种是他们是第一次安装但还没启动,另一种是用户在后台进程管理手动杀死,处于后台的应用不杀死的话依然能够接受到系统广播。而系统级的应用程序是可以接收到开机启动广播的,当然了,系统级的应用程序本身就受到特殊的待遇,更是可以通过配置android:process="persistent"来维护生命力!安装在/System/App目录下的应用就视为系统级的应用,相当于身穿黄马褂,手持免死金牌了,这种方法一般不作考虑。

2、伪进程保活

顺带说一下伪进程保活,为什么说是伪的呢?因为这种进程保活我想就是广义上的双进程守护,据说黑马还是极光的每一期视频都会有的课程就是双进程保活,但是我想他们的双进程保活其实就是利用两个服务互相拉起,当然这只是我的猜测而已,我也没看过他们的视频,有机会一定要悄悄地搞一个回来学习一下...

关于进程保活的两三事——新手升级经验卡_第4张图片
穷啊,没钱培训

这里说的这种进程保活,我也尝试实现了一下,发现当守护进程走生命周期的话,那么是可以实现互相拉起的,杀死了其中一个服务,另一个服务就会重新把这个服务打开。之所以说伪,就是因为这种方法只是尽量维持后台服务:

如提升优先级等,避免被系统杀死,在被系统杀死后能够迅速活起来。

在onDestory发送广播唤起自己

在onStartCommand中返回START_STICKY。。。等

然而要是用户直接将后台服务从进程管理中杀死的时候,那么这整一个Process就会被kill掉,这里进程的概念是相对于linux里面的一个进程,kill掉之后连带这个应用里所有的独立进程都会被杀掉,这种时候,伪进程保活就不能互相拉起了,因为都被杀死了,之前在网上看到有人说,白科技,灰科技,都是伪进程保活,而且利用系统漏洞实现的前台服务更是在很多的手机上都不可行,前台服务是可以提高服务的优先级,但是用户都看着呢,这明显遵守保活的猥琐原则。虽然是伪的,我们仍然需要做这些保护措施,当应用没有被用户手动杀死的时候,维持后台服务的正常运行。

3、黑科技环节

好像上面絮絮叨叨的,有的没的说了一大堆,是时候介绍一些不明觉厉的东西了:

1.传说中的鹅厂黑科技

在应用退到后台后,有一个1*1像素的页面显示在屏幕上,这种传的神乎其技的东西也不知道真假,目前还没看到有关于这方面的介绍或思路,尽管这种黑科技不能使进程永生不死,但是还是很有研究价值。

2.第三方SDK互相唤醒

我们在引用第三方SDK的时候,尤其是推送服务,会有一个守护进程,虽然内部实现不知道是什么原理,所以的数据走的都是一条链路,但是经过鄙人一番狂妄的分析发现,如果第三方sdk是基于ndk实现的进程守护,那么只要使用了这个sdk,就应该能够唤醒app才对,所以我想里面的守护进程只是为了守护推送服务能够正常运行,而真正的互相唤醒是基于广播机制的,由第三方应用互相唤醒的方法。

3.ndk实现进程守护

github上传闻有一个能让进程在5.0上永生不死的demo,但是很多人使用了之后都说发生各种issues,而网上也有说利用一个native service来守护应用层的service,实现所说的双进程守护,ndk需要c++功底,而且还有通道这些,作为菜鸟的我尚未涉猎,但是相信这和github上的原理是差不多的。

4.奸商的暗箱操作

传闻说QQ微信这些之所以能够在各手机厂商生产的手机上常驻后台,是归根于厂商为了用户体验而与TX合作,让QQ微信这些应用进入白名单!诸如此类的app不少,不知道360是不是也是这样子干的...

总结

总所周知的,老板把需求压下来,我们苦逼程序员吧还是得撑住啊,所以真正适合我们苦逼程序员的解决方案有:

选用第三方SDK的时候尽量选用用户量多的SDK(黑心可行,推荐)

在开发一系列APP的时候,让APP之间能够通过广播相互拉起(工程量巨大,原理上可以实现)

不过要是有大佬用ndk实现了进程的永生不死,烦请告诉小弟,即使我技术渣,但是我有一颗纯真的赤子之心啊!即使用这样的黑科技,我们还是要致力于维护android的生态平衡啊。

关于进程保活的两三事——新手升级经验卡_第5张图片

最后的最后,能用钱解决的问题就不是问题哈

你可能感兴趣的:(关于进程保活的两三事——新手升级经验卡)