BearZPY Blog

Hi, nice to meet you

BearZPY's avatar BearZPY

Gradle 生成 Jar 包

Gradle 生成 Jar 包

网上找到的在 Android Studio 里生成 jar 包的帖子,基本都是生成 aar,或者是使用第三方库,并不符和需求。项目中 Service 使用 AIDL,AIDL 的版本很难管理,所以需要把编译 AIDL 所生成的 class 文件打包成 jar 包,方便客户端使用和版本管理。

需要打包的 class 目录

Android Studio 编译生成的 class 是在对应的 Module 目录下的。

PATH: {Module}/build/intermediates/classes/{ProductFlavors}/{BuildType}/{PackageName}/

  • Module: 模块名称。
  • ProductFlavors: 产品风味,如果没定义这个量就没有这层目录。
  • BuildType: 构建类型。
  • PackageName: 需要打包的 class 的包名。

Build Type + Product Flavor = Build Variant

生成 Jar 包的目录

Gradle 打出的 Jar 包默认存放在对应的 {Module}/build/libs 文件夹下。

删除生成的 Jar 包

Gradle 生成 Jar 包的同时可以对 Jar 包进行命名,在命名上有版本号的区分,比如生成的 Jar 包名字为 mJar-V0.0.1.jar。在删除旧的 Jar 包的时候如果版本号变了,以文件名查找删除可能就找不到该文件,所以可以选择将整个 libs 文件夹删除。

任务 clearLibsDir 用来清理生成 Jar 包。

task clearLibsDir(type: Delete) {
    delete 'build/libs'
}

对生成的 class 打包

在 {Module} 文件夹下的 build.gradle 中添加 clearLibsDir 任务和 makeJar 任务,同步后执行 makeJar 任务就能生成需要的 Jar 包,makeJar 任务依赖于 clearLibsDir 任务,所以每次生成 Jar 包的时候都会把先清除旧的 Jar 包。

task makeJar(type: Jar, dependsOn: clearLibsDir) {

    // 指定生成的 jar 包名字
    baseName "mJar-V0.0.1"
    // 设定需要打包的 class 文件路径
    from('build/intermediates/classes/debug/')
    // 排除 debug 目录下的 android 文件夹
    exclude('android/')
    // 排除 com 目录下的 test 目录下的 ui 文件夹
    exclude('com/test/ui')
    //去掉 R$ 开头的文件
    exclude { it.name.startsWith('R$'); }
    // 指定打包后的目录结构
    into('/')
}

注: into 处需要保持 ‘/‘ 目录结构,指定目录结构可能会造成 Manifest.MF 重复问题。打包时 Manifest.MF 文件会放在 into 中的一级目录下,若指定其他目录结构,Manifest.MF 在其他包名下会被当作资源文件,当项目中存在多个 jar 包有可能造成多个 Manifest.MF 被认为是资源文件且路径相同的错误。

拷贝生成的 Jar 包到指定的目录中

编写 copy 任务,把生成的 jar 包从生成目录拷贝到指定目录中,这里的路径可以是相对路径。

task copyJarTask(type: Copy, dependsOn: makeJar) {
    from 'build/libs'
    into 'build/../libs'
}