前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >小程序如何实现多进程?从隔离角度出发,看完你就会懂!

小程序如何实现多进程?从隔离角度出发,看完你就会懂!

作者头像
极乐君
发布2020-03-10 21:43:44
4.1K0
发布2020-03-10 21:43:44
举报
文章被收录于专栏:极乐技术社区极乐技术社区

小程序这个名词相信大家已经不陌生了,继微信之后,阿里巴巴、百度、头条等大厂相继实现了自己的小程序。小程序是一种全新的开放能力,开发者能够快速开发出小程序并集成进宿主,实现推广等目的。

从使用角度看,小程序有轻量,易用等特点;

从技术角度,以Android端为例,小程序有部分组件原生化、UI和逻辑线程隔离、小程序之间进程隔离等等。

本篇文章主要从小程序进程隔离角度出发,分析BAT的小程序多进程的实现方案,并自己实现一个小程序的多进程。

01

多进程的意义

多进程,顾名思义,即每一个小程序都是一个单独的进程。这个效果只在Android端独有。那为什么我们希望小程序之间实现进程隔离呢?原因大致有三点:

  1. 由于是单独进程,无论小程序内部因为何种原因的崩溃,对主进程都没有影响,增强用户体验。
  2. 由于每个进程都有一片单独的内存区域,小程序不会占用主进程的内存,降低了内存溢出的风险。
  3. 由于不同进程间的内存是隔离的,当同时开启多个小程序时,内存变量、参数等数据互不影响,也可达到一个解耦的目的。

02

对微信小程序的分析

既然是分析多进程这种用户感知不强烈的技术点,我们需要通过一些工具或命令。

一. 进程分析

首先,我们把微信完全杀死又重新开启,然后通过 adb shell ps | grep com.tencent.mm 命令,可以查看正在运行的进程名称和数量,其中 grep com.tencent.mm 是过滤微信相关的进程,因为微信的包名是com.tencent.mm。此时进程运行状况如下图:

此时我们只能看出微信从完全关闭到启动,开启了6个进程,但是还看不出这些是否与小程序相关。于是,我们打开一个小程序,再次执行 adb shell ps | grep com.tencent.mm 命令,此时进程运行状况如下图:

对比之后,就可以做一些分析了。其中,com.tencent.mm是主进程,com.tencent.mm:push应该是与推送相关的进程,com.tencent.mm.tools和com.tencent.mm:toolsmp应该都是一个类似于Helper的相关进程,因此我认为最有可能的是com.tencent.mm:appbrand2,因为这个命名比较特殊,前面分别有appbrand0和appbrand1两个进程出现过。那么为什么新开的第一个小程序,反而多出来的进程是appbrand2呢?我个人猜测这与微信小程序的预加载有关系,很有可能是,这个进程是空的,只是先fork出来,并没有做过多的事情,真正承载我们开启的那个小程序的进程,很有可能不是这个appbrand2。那么如何验证呢?进入第二步,Activity分析。

二. Activity分析

首先打开一个小程序,然后通过 adb shell dumpsys activity activities 命令,可以看到所有栈内的Activity信息,滑到顶部,查看正在与用户交互的Activity信息,如下图:

关键的信息我已经用红色圈了出来,这大致已经验证了我们刚才的猜想,即:com.tencent.mm:appbrand系列,是与小程序相关的进程。

微信预加载2个空进程作为预加载,避免用时再fork进程,耗时过长影响用户体验。

为了进一步验证猜想是否正确,我下载了微信最新版本的apk,进行了逆向操作,也就是第三步,分析apk。

三. 微信Apk分析

反编译的方法大家自行搜索,这里就不赘述了。我们打开反编译后的AndroidManifest.xml文件,搜索刚才的的Activity名称,结果如下:

得到的信息与刚才一致。然而,我们又发现了另一个问题,那就是AppBrandUI还有另外4个兄弟,即AppBrandUI1,AppBrandUI2,AppBrandUI3,AppBrandUI4,而这四个Activity的名称与绑定的进程,又能够与一开始的appbrand对应起来,经过试验,我发现微信最多只可以启动5个小程序,而这些小程序的载体就是这5个Activity,不断轮询,超过5个时,将第一个结束掉。这样,我们就基本可以确定,微信是通过apk内置的5个Activity,来实现小程序的多开与进程隔离的。

因此,理论上这5个Activity应该是除了进程不同,内部逻辑应该都是相同的,于是我们继续验证,反编译代码后找到AppBrandUI1这个Activity,结果如下图:

AppBrandUI2,AppBrandUI3,AppBrandUI4与此完全一样,都是继承了AppBrandUI,做了极少的事,由于微信代码混淆过,我们无法看出那几行代码具体做了什么,但是基本可以理解为完全复用。至于为什么分开写,而不是复用同一个。

我猜测原因可能有二:

  1. 由于语法限制,为Activity开辟进程需要在AndroidManifest.xml中预先配置
  2. 微信不仅将小程序进程隔离,并且还进行了栈隔离,当我们同时开启多个小程序时,长按Home键,可以发现存在多个小程序任务卡片,这种效果同样需要在AndroidManifext.xml中配置taskAffinity属性,这在上图中也有体现。

另外,我还注意到,微信在AndroidManifest.xml中配置了这样的Receiver:

这种Receiver共有5个,每个小程序进程有一个,其它4个只是继承了这个AppBrandTaskPreloadReceiver,由于混淆的原因,无法看出具体做了什么事,但是通过名字判断,是实现小程序进程预加载的,空闲时开启这个广播,至少可以提前开启进程,避免用时再加载耗时过长影响用户体验。

同样的,我分析了百度和支付宝的apk,通过命令和反编译等方法,发现他们的方案几乎一样,只是预加载的数量等一些小细节不同,感兴趣的同学可以自己逆向之后做对比。

03

分析总结

1. 微信对每个小程序都做了进程隔离和栈隔离,互不影响。

2. 实现这一功能的载体Activity是预先配置在AndroidManifest.xml中的。

3. 通过某种方法,微信将小程序的最大运行数量控制在5个。

4. 微信对多进程做了一些优化,已知的是预加载2个空进程。

5. BAT等大厂的小程序多进程方案大同小异。

04

实现小程序多进程的关键点

一. Application初始化

Android的app在开启多进程时,每开启一个进程,Application都会重新创建,也就是onCreate函数会被调用,如果没有做进程判断,所有东西会初始化多次,造成卡顿或意料之外的bug。

二. 分配与管控

由于进程之间的内存无法共享,小程序的生命周期需要在某一个进程中维护,不然无法做到动态分配进程和栈,而这个进程选择主进程最为合适。因此需要创建一个管理器,这个管理器负责以下几件事:

1. 接收外界开启、关闭等对小程序的操作

2. 合理的为接收到的请求分配空闲的进程

3. 接收远程小程序的生命周期回调并通过某个uuid进行维护

4. 在空闲时预加载进程

5. 根据设置的可开启的最大小程序数量,对进程进行新建、销毁等操作

6. 所有这些管理和维护的操作,对小程序接入者都应是透明的,无需关心具体实现流程,仅在需要时开启小程序即可。

三. 进程生命周期问题

Android系统对于内存有一套自己的管控机制,当内存较为紧张时会在不做任何通知的情况下kill掉活跃度较低的进程,至于进程活跃程度,就与Android的进程保活有关了,可通过设置前台进程、唤醒等方式去尽量保活。但是无论应用端再怎么做,都无法逾越操作系统的权限,系统在某些情况下依然会把进程杀死来保证整个系统的正常运行。因此,开发时需要做容错处理,不能仅以Activity的onDestroy回调为准,因为一旦出现系统级的回收,很可能导致整个分配管理器的错乱。

四. 通讯

通信又分为两个方面,第一,小程序进程与app主进程是隔离的,需要进程间的IPC通信;第二,小程序的本质是一个web容器,这就少不了js与原生的通信,需要jsbridge。下面分别说一下这两个方面。 进程通信:

IPC的实现已经不是什么问题,这里仅说几个需要注意的点:

1. 通信一定是双向的,无论哪个进程,最好绑定同一个服务,方便数据的维护。

2. 由于通信较为频繁,建议使用基于Binder的通信机制,可以提高运行效率。

05

js与原生通信:

js与原生通信一定是通过jsbridge,最好做法是将原生方法的实现写在主进程,分布在不同进程的小程序向主进程请求某个bridge的实现结果,主进程根据相应的参数去执行并返回结果,类似于一套CS的架构。即小程序客户端无需关心具体操作,只关心结果并响应给web端。

本文参与?腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2020-02-29,如有侵权请联系?cloudcommunity@tencent.com 删除

本文分享自 极乐技术社区 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与?腾讯云自媒体分享计划? ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 二. Activity分析
  • 三. 微信Apk分析
相关产品与服务
云开发 CloudBase
云开发(Tencent CloudBase,TCB)是腾讯云提供的云原生一体化开发环境和工具平台,为200万+企业和开发者提供高可用、自动弹性扩缩的后端云服务,可用于云端一体化开发多种端应用(小程序、公众号、Web 应用等),避免了应用开发过程中繁琐的服务器搭建及运维,开发者可以专注于业务逻辑的实现,开发门槛更低,效率更高。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
http://www.vxiaotou.com