内容简介:医动力App作为公司的核心产品已经有多年历史了,随着版本的不断迭代,功能越来越多,代码量越来越大,不可避免的会产生一下问题:因此,为了提高项目的可维护性和开发效率,组件化成为了必然.首先看看老版本的医动力的项目工程结构
医动力App作为公司的核心产品已经有多年历史了,随着版本的不断迭代,功能越来越多,代码量越来越大,不可避免的会产生一下问题:
- 业务越来越复杂,维护成本高;
- 业务耦合度高,代码越来越臃肿,团队内部多人协作开发困难;
- 编译时间长,每修改一处代码后都要重新编译打包测试,导致非常耗时;
- 开发测试困难,每次修改都必须打包整个项目运行.
因此,为了提高项目的可维护性和开发效率,组件化成为了必然.
组件化的目标
首先看看老版本的医动力的项目工程结构
项目分为Doctor和Patient,它们之间公共的代码放在common中,common中会依赖一些第三方的库.随着项目的迭代,Doctor和Patient里面的代码会越来越耦合,因为单个module中仅仅是以包名作为功能的划分,而包之间是可以随意调用的.
AndroidStudio/IDEA是多模块管理的,组件化的思路就是把不同的业务模块拆分到各个子Module中,同时这些业务Module之间不会存在直接的调用,这样当我们移除项目中的某个业务Module的时候不会影响整体的项目运行,如下图所示:
可以看到有「ModuleIM」,「ModuleFollow」,「ModuleDiary」三个业务模块,它们都会引用Common模块而获取一些基础库的支持,同时这些业务模块是可以单独运行的.后续会将更多的模块独立出来,完成彻底的组件化.
如何组件化?
Android的组件化的技术点主要在两个方面:
- 配置组件独立运行的能力;
- 组件之间的通信
第一点是通过在module的gradle.build中切换
apply plugin: 'com.android.application' apply plugin: 'com.android.library', 复制代码
并设置对应模式下加载的AndroidManifest.xml和src的路径.
第二点由于组件之间是没有直接依赖的关系的,要想让它们通信就必须把它们注册在一个公共的地方,这里可以通过路由,也可以通过注册接口.
目前组件化的方案在网上有很多,由于组件化并不涉及Android系统级别的操作,因此是比较成熟稳定的.我们知道,组件化是需要花费大量时间和精力的,很难做到把项目彻底的拆分成组件,那有没有一种方式可以让我们不改动原有项目(改动很小)的情况下,将新功能进行组件化开发?
因此我们选择了使用CC来进行组件化的改造
Component Caller(CC)介绍
引用自CC官方的两张图能让我们很快的明白什么叫做渐进式组件化?
在渐进式组件化的方案中,可以先不用解耦,只需要让单独运行的组件能够调用到主App中的功能即可。思路是这样的:
- 新业务以组件形式开发
- 新组件需要调用的主App中的业务,在对应的模块中创建一个组件类,对外暴露对应的服务,供其它组件调用,并不需要现在就将这个模块解耦
- 新组件通过跨App的方式调用主App中的组件
- 主App也可以通过跨App的方式调用到单独运行的组件App中的组件
- 在同一个module中可以创建多个组件类,将来解耦时将对应的组件类移动到解耦后的module中即可
关于CC的技术实现细节可以查看其github主页的wiki系列文章 github.com/luckybilly/…
组件化实践
CC的集成
1.在项目的根gradle.build中加入:
buildscript { dependencies { ... ... classpath 'com.billy.android:autoregister:1.4.1' } } 复制代码
这个autoregister插件是用来在编译期间动态扫描并修改class文件,实现组件的自动注册,具体配置后面会提到
2.在Doctor和Patient这两个主App的gradle.build中加入
ext.mainApp = true //设置为true,表示此module为主app module,一直以application方式编译 apply from: '../cc-setting.gradle' 复制代码
cc-setting.gradle中主要进行了以下几点操作:
- 读取local.properties文件中的配置来区分组件是否以独立app的方式编译;
- 添加com.billy.android:cc:1.1.0依赖;
- 自动注册组件的配置
3.实现IComponent接口创建组件类
我们统一在Doctor和Patient中的exports包内创建App对外提供的组件,不同业务的组件放在创建在对于的类中管理
IComponent的实现也很简单,提供一个模块名称name和对不同action的处理
主App的配置就这么多,接下来要新建一个组件Module
4.业务module的配置
这里需要设置module独立运行时的applicationId,同时指定resourcePrefix资源前缀(防止不同模块之间资源文件的冲突)
因为设置了module的独立运行,就需要准备一份module在独立运行模式下的AndroidManifest文件,路径在src/main/debug下
5.业务module提供IComponent接口
和主App一样,模块要提供服务给其他模块调用,需要提供实现IComponent的子类,因为业务module提供的服务会比较少且单一,我们将它放在包名下的ExportComponent下
7.主App设置需要依赖的module
dependencies { api fileTree(include: ['*.jar'], dir: 'libs') addComponent 'module_follow' addComponent 'module_diary' addComponent 'module_im' } 复制代码
通过addComponent方式添加依赖,其内部会根据业务module的运行模式决定是否依赖
6.设置业务module的运行模式
业务module的运行模式包括开发模式和集成模式
- 开发模式:会以App的方式运行
- 集成模式:打包在主App中
打开local.properties文件
module_follow=true module_diary=true module_im=false 复制代码
设置模块名称等于true或者false(没有设置则为false)
- 当等于true则该模块会以App运行,这时候打包主App的时候是不会把该模块打包进去
- 当等于false时则不能独立运行,打包主App的时候会一起打包进去
运行调试
现在你可以将组件单独运行起来了,但是由于业务组件是不包含登录功能的,因此它是没有用户登录状态的,所以我们需要通过CC的组件调用去主App中获取
补充一点,如果想要跨App调用首先需要打开CC的设置
CC.enableRemoteCC(true); 复制代码
网络请求组件化
项目中用到的网络请求框架是okhttp+retrofit,我们希望不同module中使用不同的retrofit的Service实例,比如在Module_follow中我们会创建FollowService.java来处理当前模块的网络请求
在集成开发模式下我们可以通过组件调用去获取主App中的Retrofit对象,我们只需要在主App中定一个name=http,action=getRetrofit的IComponent;
但在开发模式下,跨进程调用组件是传输不了Retrofit对象的,因为Android的跨进程只能传输Parcelable对象,这里我们可以在本module中提供一个相同名称的IComponent,在里面去获取主App的baseUrl和token,并创建新的Retrofit对象,这样就可以透明的处理获取Retrofit对象了.
为什么以上方式可行呢?因为CC在进行组件化调用的时候,会检查当前模块是否存在要调用的模块,如果存在则会调用本地的,不存在才会去跨进程调用.最后我们可以把这些模拟操作抽到一个lib_mock的module里面复用.
以上所述就是小编给大家介绍的《医动力Android基于CC组件化框架的探索与实践》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!
猜你喜欢:- 组件化之路—集成组件SDK
- Android组件化入门:一步步搭建组件化架构
- Android快速开发框架,基础库,样式库,组件化,组件集成
- Android组件化方案及组件消息总线modular-event实战
- 组件化实践
- 组件化架构漫谈
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
计算机程序设计艺术(第1卷)
[美] Donald E. Knuth / 清华大学出版社 / 2002-9 / 80.00元
第1卷首先介绍编程的基本概念和技术,然后详细讲解信息结构方面的内容,包括信息在计算机内部的表示方法、数据元素之间的结构关系,以及有效的信息处理方法。此外,书中还描述了编程在模拟、数值方法、符号计算、软件与系统设计等方面的初级应用。此第3版增加了数十项简单但重要的算法和技术,并根据当前研究发展趋势在数学预备知识方面做了大量修改。一起来看看 《计算机程序设计艺术(第1卷)》 这本书的介绍吧!