一、插件化起源
插件化技术最初源于免安装运行 Apk
的想法,这个免安装的 Apk
就可以理解为插件,而支持插件的 app
我们一般叫 宿主。
想必大家都知道,在 Android
系统中,应用是以 Apk
的形式存在的,应用都需要安装才能使用。但实际上 Android
系统安装应用的方式相当简单,其实就是把应用 Apk
拷贝到系统不同的目录下、然后把 so
解压出来而已。
常见的应用安装目录有:
-
/system/app
:系统应用 -
/system/priv-app
:系统应用 -
/data/app
:用户应用
那可能大家会想问,既然安装这个过程如此简单,Android
是怎么运行应用中的代码的呢,我们先看 Apk
的构成,一个常见的 Apk
会包含如下几个部分:
-
classes.dex
:Java
代码字节码 -
res
:资源文件 -
lib
:so
文件 -
assets
:静态资产文件 -
AndroidManifest.xml
:清单文件
其实 Android
系统在打开应用之后,也只是开辟进程,然后使用 ClassLoader
加载 classes.dex
至进程中,执行对应的组件而已。
那大家可能会想一个问题,既然 Android
本身也是使用类似反射的形式加载代码执行,凭什么我们不能执行一个 Apk
中的代码呢?
二、插件化优点
插件化让 Apk
中的代码(主要是指 Android
组件)能够免安装运行,这样能够带来很多收益:
- 减少安装
Apk
的体积、按需下载模块 - 动态更新插件
- 宿主和插件分开编译,提升开发效率
- 解决方法数超过65535的问题
想象一下,你的应用拥有 Native
应用一般极高的性能,又能获取诸如 Web
应用一样的收益。
嗯,理想很美好不是嘛?
三、与组件化的区别
-
组件化:是将一个
App
分成多个模块,每个模块都是一个组件(module),开发过程中可以让这些组件相互依赖或独立编译、调试部分组件,但是这些组件最终会合并成一个完整的Apk
去发布到应用市场。 - 插件化:是将整个App拆分成很多模块,每个模块都是一个Apk(组件化的每个模块是一个lib),最终打包的时候将宿主Apk和插件Apk分开打包,只需发布宿主Apk到应用市场,插件Apk通过动态按需下发到宿主Apk。
四、插件化的技术难点
想让插件的Apk真正运行起来,首先要先能找到插件Apk的存放位置,然后我们要能解析加载Apk里面的代码。
但是光能执行Java代码是没有意义的,在Android系统中有四大组件是需要在系统中注册的,具体来说是在 Android
系统的 ActivityManagerService (AMS)
和 PackageManagerService (PMS)
中注册的,而四大组件的解析和启动都需要依赖 AMS
和 PMS
,如何欺骗系统,让他承认一个未安装的 Apk
中的组件,如何让宿主动态加载执行插件Apk中 Android
组件(即 Activity
、Service
、BroadcastReceiver
、ContentProvider
、Fragment
)等是插件化最大的难点。
另外,应用资源引用(特指 R
中引用的资源,如 layout
、values
等)也是一大问题,想象一下你在宿主进程中使用反射加载了一个插件 Apk
,代码中的 R
对应的 id
却无法引用到正确的资源,会产生什么后果。
总结一下,其实做到插件化的要点就这几个:
- 如何加载并执行插件
Apk
中的代码(ClassLoader Injection
) - 让系统能调用插件
Apk
中的组件(Runtime Container
) - 正确识别插件
Apk
中的资源(Resource Injection
)
插件化是一门很有意思的学问,网上已经有很多“入门知识”和“实现原理”之类的文章,但是关于插件化的实战却没有一个系统、全面的分享,下面我要分享的是最近小编有幸在腾讯高工手里扒到这份“插件化实战学习手册",这位大佬主导开发过多个采用插件化架构的APP项目。手册中收录了各互联网大厂热门的插件化项目实战,从新手到架构师,这份学习手册足以。
第一章、插件化技术的前世今生
- 插件化提要
- 插件化发展历史
第二章 插件化原理
- 类加载
- 双亲委托机制
- 资源加载
- 四大组件支持
- Proxy Activity代理
- hook方式
第三章 Android插件化初探
- 从零开始实现一个插件化框架
- Activity的启动流程
- 寻找Hook点
- 撸码阶段
- 代理对象
- 偷天换日,替换原来的Intent
- ActivityThread
- 将代理的intent替换回来
有需要的朋友直接点击此处的蓝色字体获取完整文档。
第四章 架构演化(大厂篇)
-
360插件开发之DroidPlugin
插件开发之360 DroidPlugin源码分析
插件开发之360 DroidPlugin源码分析之Hook机制
Hook机制的包结构关系
Hook机制类图关系
Hook机制的时序图关系
Manifest权限申请
基类Hook做了什么?
…
-
滴滴VirtualApk实战
配置
应用
原理
总结
问题
-
基于VirtualAPK Android重构之插件化
Plug-in Hello World
插件化框架的选择
插件化原理
引入插件化之痛
-
爱奇艺插件化原理分析之 Neptune框架
插件化基础知识点
类加载
插件化中资源使用限制
Apk打包流程
四大组件的插件化
插件Activity任务栈
处理插件中的广播
处理插件中的Service
-
腾讯插件化框架 Shadow项目解析
sample示例代码AndroidManifest.xml分析
Activity 实现
替换插件 Activity 的父类
Service 实现
BroadcastReceiver 实现
ContentProvider 实现
框架自身动态化
以上就是腾讯内部强势推出的“插件化实战学习手册”,有需要的朋友直接点击此处的蓝色字体获取完整文档。
写在最后
插件化是一门很有意思的学问,用一句话来形容就是偷天换日灯下黑,在各种坑的限制下不断跟系统博弈寻找出路。随着了解的深入,大家肯定能理解我这句话,本文也只是抛砖引玉,更多的乐趣还是要自己去发掘。