android studio 生成具有依赖性的 aar

标签 android gradle android-studio

我有一个库项目(A) 引用了另一个jar 文件(B.jar),但是在生成aar 文件后,jar 文件(B.jar) 没有 bundle 在输出的aar 文件中,当使用这个aar 文件时,我得到了一个 NoClassDefFoundError

有没有办法让gradle在输出的aar文件中 bundle 所有依赖类? 这是我的 build.gradle:

apply plugin: 'com.android.library'

repositories {
    mavenCentral()
}

android {

    buildTypes {
        release {
            runProguard true
            proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.txt'
        }
    }
}

dependencies {
    compile project(':common')
    compile fileTree(dir: 'libs', include: ['*.jar'])
}

最佳答案

Is there a way to make gradle bundle all dependency classes in the output aar file?

是的,有办法做到这一点,我以前遇到过这个问题。但这将是一个很长的故事,请耐心等待。

背景

当您在 build.gradle 中指定依赖项时,您是在告诉 Gradle 从 Maven 存储库下载 Artifact (AAR/JAR)。所以,Gradle 需要两件事:

  1. Maven 存储库位置
  2. 依赖本身

您在顶级 build.gradle 中指定 Maven 存储库

repositories {
    jcenter()
    google()
}

并且你指定了对项目级build.gradle

的依赖
dependencies {
    compile 'com.example:mylibrary:1.0.1'
}

Gradle/Maven 如何知道 mylibrary 需要其他依赖项?来自您的依赖 POM file .

POM 示例

以Square的OkHttp为例,你可以在mvnrepository.com中找到这个神器。

OkHttp Artifact

OkHttp 有一个 POM 文件。您可以单击该链接以显示完整的 XML,我只向您展示有趣的部分,即依赖项 block 。

<project>
   <modelVersion>4.0.0</modelVersion>
   <parent>...</parent>
   <artifactId>okhttp</artifactId>
   <name>OkHttp</name>
   <dependencies>
      <dependency>
         <groupId>com.squareup.okio</groupId>
         <artifactId>okio</artifactId>
      </dependency>
      <dependency>
         <groupId>com.google.android</groupId>
         <artifactId>android</artifactId>
         <scope>provided</scope>
      </dependency>
      <dependency>
         <groupId>com.google.code.findbugs</groupId>
         <artifactId>jsr305</artifactId>
         <scope>provided</scope>
      </dependency>
   </dependencies>
   <build>...</build>
</project>

OkHttp 需要来自其他 Artifact 的依赖项。 Okio、Android 和 jsr305。但是,当您在项目中包含 OkHttp 时,您不必在项目中包含 Okio、Android 和 jsr305。这是为什么?

因为 Gradle/Maven 会查看 POM 文件并为您下载依赖项。不再有 NoClassDefFoundError

您的图书馆项目

回到您的问题,如何将您的库项目“组合”成单个 .aar?以下是步骤:

  1. 将您的依赖项(您的 JAR 或 AAR)发布到 Maven 存储库中。

您的依赖项很可能已经存在于 mvnrepository 上,如果它不存在,您可以在 bintray、mvnrepository 上提交依赖项,或者托管您自己的 Maven 存储库。

  1. 为您的 AAR 创建一个 POM 文件。

就像在 OkHttp 依赖 block 中一样,您将库依赖项放在那里。

  1. 将您的库 AAR 提交到 Maven 存储库。

您可以使用mvndeploy 将您的库提交到Maven 存储库。

mvn deploy:deploy-file \
    -DgroupId=com.example \
    -DartifactId=your-library \
    -Dversion=1.0.1 \
    -Dpackaging=aar \
    -Dfile=your-library.aar \
    -DpomFile=path-to-your-pom.xml \
    -DgeneratePom=true \
    -DupdateReleaseInfo=true \
    -Durl="https://mavenUserName:mavenPassword@nexus.example.com/repository/maven-releases/"

如果您不想手动执行第 2 步和第 3 步,您可能会猜到,“有一个 gradle 插件可以做到这一点!”。插件是android-maven-publish , 感谢:wupdigital 使这些过程更容易。

现在您可以使用 gradle 命令发布您的库了:

gradle yourlibrary:assembleRelease yourlibrary:publishMavenReleaseAarPublicationToMavenRepository

如何分享您的图书馆项目

下次你的队友要你的图书馆时,你可以给他们两样东西:

  1. 包含您的库及其依赖项的 Maven 存储库
  2. 您的库组、 Artifact 和版本名称

就是这样!无需将您的依赖关系提供给您的同行。

干杯🥂

关于android studio 生成具有依赖性的 aar,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26020466/

相关文章:

java - 使用警报对话框从 ListView 中删除项目

android - 当一个 Activity 加载其他 Activity 时添加进度条

android - onSharedPreferenceChange 监听器 -> 在 fragment 中

plugins - 手动安装 Gradle 插件

android - 在android studio中安装存储库和同步项目错误说所有包都不可用

android - 在 jQuerymobile .button() 调用后删除按钮

java - Android Studio/Gradle 项目中的纯 Java 8 库模块

ssl - Gradle 任务 - Https 请求 - 附加客户端证书

android - 警告 : 'onCreateView' always returns non-null type

java - 运行任何新的 Android 项目时出现问题 - 未找到默认 Activity/无效的 Java 包