Android第三方项目依赖方式

对于目前常用的gradle项目,依赖第三方库的方式主要分为三种:

  • 直接通过将第三方库的jar包,so库拷贝到项目中进行gradle配置依赖
  • 直接将第三方库的aar包拷贝到项目中进行gradle配置依赖
  • 第三方库已将aar包提交到maven服务器上(例如maven center, jcenter),由项目通过gradle索引进行依赖

当android gradle项目越来越大时,上述第一种,第二种方式容易由于jar包的package冲突,或者aar的资源冲突导致整个项目的最终build失败,因此我们应该尽量使用第三种方式进行第三方依赖

gradle依赖版本冲突,默认处理

当android gradle项目越做越大时,通常会将项目分成多个组件开发,一个项目中也常常包含多个module。为了项目的可扩展性和可维护性,每个module通常相对独立,而很难保证每个module所依赖的第三方库没有冲突。而最常见的冲突通常发生为依赖同一个第三方库的不同版本。例如android v4包。

当gradle项目遇到依赖第三方库版本不同所造成的冲突时,默认行为是,强制使用项目中使用的第三方库最高版本。

为了查看android gradle项目中的所有依赖,可以在工程的主module对应的目录下运行:

1
gradle dependencies

下图展示我们项目中的一个运行结果的一部分:

gradle dependencies结果示意图

结果中标记(*)的部分, 都为冲突的第三方依赖,从结果中可看出,com.daimajia.swipelayout:1.2.0版本依赖的v4包版本为21.0.3,小于项目其他module所使用的v4包版本依赖。在gradle编译过程中,发生此类版本冲突时,默认使用项目使用的最高版本,即本例中的v4包24.0.0版本进行编译。

gradle依赖版本冲突,特殊处理

一般情况下,默认的处理方式能使项目正常编译,但是并不是所有项目都能这样安然无恙。比如当依赖的第三方库版本上存在较大差异时,使用最新版本编译会造成class not found,或者接口冲突等异常。此时常用的解决方法是,使用force命令强制使用某一个指定第三方库版本;或者使用exclude命令或transitive命名,屏蔽传递依赖(transitive dependency),从而避免由于版本冲突导致使用最高版本的情形。如下例子(详情请参考dependencyHandler):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
apply plugin: 'java' //so that I can declare 'compile' dependencies
dependencies {
compile('org.hibernate:hibernate:3.1') {
//in case of versions conflict '3.1' version of hibernate wins:
force = true
//excluding a particular transitive dependency:
exclude module: 'cglib' //by artifact name
exclude group: 'org.jmock' //by group
exclude group: 'org.unwanted', module: 'iAmBuggy' //by both name and group
//disabling all transitive dependencies of this dependency
transitive = false
}
}

gradle依赖刷新

极少情况下,第三方依赖库发生更新,但是由于某种原因并未升级其对应版本号,此时可以通过一下方式进行刷新

1
2
删除本地 ~/.gradle/caches/modules-2/files-2.1/ 目录下的对应的第三方依赖缓存
在项目主目录下运行:gradle --refresh-dependencies