Android插件化实现方案

插件化对于广大Android开发者而言,应该是一个不陌生的名词。许多APP都有用到插件化技术,例如逢年过节,许多APP都会动态换上许多营造节日氛围的ui特效,但是却不需要用户去重新下载APP;再者下载一款游戏平台APP,若一次性下载一个包含所有游戏的平台APP,那肯定需要很长时间,而用户往往只玩其中一两款,这时候就需要“按需下载”,在用户想玩的时候在下载相应游戏的插件,这样体验就好多了。

       目前来说实现Android实现插件化的方案大致分为两个方向:

       1、动态替换方案:提供对Android底层的各种类进行Hook,来实现加载插件中的四大组件,以DroidPlugin框架为代表;

       2、静态代理方案:通过ProxyActivity统一加载插件中的所有Activity,以that框架为代表。

       本文以方案二静态代理来实现Activity的插件化。

       本文项目结构如下:

       本文项目分为三大模块,主APP模块,插件APP模块,以及充当两者桥梁,起到解耦作用的pluginlib Library部分。

接下来我们分别讲解这三个部分。

一、主APP模块

       我们知道项目build完后会生成apk文件,作为主APP模块,我们需要加载外部的插件apk,正常的加载流程应该如下:

扫描二维码关注公众号,回复: 12655246 查看本文章

       1、从服务器下载插件dex到手机SDCard,为此需要申请SDCard读写权限;

       2、读取插件apk中的dex文件,生成对应的DexClassLoader;

       3、使用DexClassLoader的loadClass方法读取插件dex中的任何一个类。

       为了模拟从服务器下载插件的方法,我们首先build插件APP,生成相应的apk文件,然后将apk文件重命名放到主APP模块的assets文件中,APP启动后会把asset目录中的插件复制到内存中,如下图所示:

相关代码如下:

二、Library模块

       首先需要一个插件APK的实体类,代码如下:

       其中DexClassLoader用于加载插件中的类,Resources和AssetManager用于加载插件中的资源,PackageInfo用于获取插件中的包信息。

       同时需要一个PluginManager类来管理实体对象,代码如下:

       另外,我们需要意识到,插件中的Activity不同于我们正常启动的Activity有AMS管理调用其生命周期,对于插件Activity,我们需要管理它的生命周期,为此我们写了一个ProxyActivity来充当这个管理的角色,如下:

       为了更好地管理和调用插件Activity,我们需要制定一套规范,让插件Activity遵循我们这套规则,为此写了如下接口:

        同时写了一个BasePluginActivity来让插件Activity继承:

       如上代码所示,若Activity属于主APK,即mFrom=FROM_INTERNAL,则走常规的启动流程,若属于插件APK,则走插件管理的启动流程。

三、插件APP模块

       插件APP这边比较简单,继承于BasePluginActivity,代码如下:

        整体效果如下,点击加载APK文件成功后,点击跳转,跳转到插件Activity。

      

     

四、总结

       插件化是Android开发中比较重要的一块,涉及的东西很多,如Android四大组件的插件化,动态代理,四大组件的启动过程,反射机制等,本文的介绍只是冰山一角,后续需要研究学习的地方还很多,有兴趣的朋友可以一起探讨。

       PS:许多同行对插件化有个误区,认为插件化能极大减少APK的体积,把需要“按需下载”的APK在需要时才下载到主APK中,其实不然。确实插件化一定程度上能减少APK的体积,但是假设一个插件APK大小为10M,让用户从服务器下载一个10M的插件新版本,需要耗费很长时间。合理的做法应该把插件1.0版本放在主APP中,APP发版后需要更新插件,通过增量更新的方式来加载。

       最后,附上项目Github地址,有问题可交流:https://github.com/xudongstorm/PlugProject

原文转载自:https://blog.csdn.net/m0_37451060/article/details/99614847?utm_medium=distribute.pc_relevant.none-task-blog-BlogCommendFromMachineLearnPai2-2.control&depth_1-utm_source=distribute.pc_relevant.none-task-blog-BlogCommendFromMachineLearnPai2-2.control

猜你喜欢

转载自blog.csdn.net/n_fly/article/details/113865650