我想从Android库项目中创建一个Jar。它的设置方式如下:
ProjectName
\- lib
| \- lib
| \- armeabi
| \- libNativeFirst.so
| \- libNativeSecond.so
\- src
\- main
\- java
\- com.package.sdk
\- PackageSDK.java
我希望所有这些都打包在Jar中,但不会泄露PackageSDK.java
中的源代码。
我设置了build.gradle
文件,如下所示:
buildscript {
repositories {
mavenCentral()
}
dependencies {
classpath 'com.android.tools.build:gradle:0.5.+'
}
}
apply plugin: 'android-library'
repositories {
mavenCentral()
}
android {
compileSdkVersion 18
buildToolsVersion "18.0.1"
defaultConfig {
minSdkVersion 10
targetSdkVersion 18
}
sourceSets {
main {
java {
srcDir 'src/main/java'
}
resources {
srcDir 'src/../lib'
}
}
}
}
task jar(type: Jar) {
from android.sourceSets.main.allSource
}
当我在项目目录中运行gradlew clean jar
时,会在名为ProjectName\build\libs
的{{1}}中创建一个Jar文件。它的结构如下:
ProjectName.jar
我希望在执行ProjectName.jar
\- lib
| \- armeabi
| \- libNativeFirst.so
| \- libNativeSecond.so
\- com
\- package
\- sdk
\- PackageSDK.java
任务时包含已编译的PackageSDK.class
而不是PackageSDK.java
文件。我可以改变什么来实现这个目标?
Per Ben Manes的建议,我将jar
的配置更改为以下内容:
sourceSets
以下sourceSets {
main {
java {
srcDir 'src/main/java'
}
resources {
srcDir 'src/../lib'
}
output {
classesDir 'build/classes'
resourcesDir 'build/javaResources'
}
}
}
任务:
jar
Gradle现在给我这个输出:
task jar(type: Jar) {
from android.sourceSets.main.output
}
答案 0 :(得分:69)
注意:答案已被修改。请参阅下面的07/28/2014更新。
这是我最终提出的解决方案。可能有更好的方法,但我还没有找到它。
android {
compileSdkVersion 18
buildToolsVersion "18.0.1"
defaultConfig {
minSdkVersion 10
targetSdkVersion 18
}
sourceSets {
main {
java {
srcDir 'src/main/java'
}
resources {
srcDir 'src/../lib'
}
}
}
}
task clearJar(type: Delete) {
delete 'build/libs/ProjectName.jar'
}
task makeJar(type: Copy) {
from('build/bundles/release/')
into('build/libs/')
include('classes.jar')
rename ('classes.jar', 'ProjectName.jar')
}
makeJar.dependsOn(clearJar, build)
正在运行gradlew makeJar
会在ProjectName.jar
目录中创建build/libs
。这个罐子的结构如下:
ProjectName.jar
\- lib
| \- armeabi
| \- libNativeFirst.so
| \- libNativeSecond.so
\- com
\- package
\- sdk
\- PackageSDK.class
这是我需要的确切结果。我现在能够在其他项目中成功使用ProjectName.jar
。
编辑:虽然我能够在Android Studio中的项目中使用生成的jar,但由于有关jar文件中存在本机代码的警告,我无法在ADT中创建的项目中执行此操作。据说有一个标志可以关闭此检查设置,但它无法正常工作。因此,如果要创建使用本机代码的库,则使用ADT的库必须手动将armeabi目录复制到libs /中。
自Android Studio 0.8.0起,Gradle输出目录已更改,上述配置无效。我已将配置更改为以下内容:
task clearJar(type: Delete) {
delete 'build/outputs/ProjectName.jar'
}
task makeJar(type: Copy) {
from('build/intermediates/bundles/release/')
into('build/outputs/')
include('classes.jar')
rename ('classes.jar', 'ProjectName.jar')
}
重要提示:请注意,ProjectName.jar
现在会被放入build/outputs/
而不是build/libs/
。
答案 1 :(得分:8)
只是为@BVB的答案添加了一个小的替代方案(虽然很大程度上基于它),这是我必须要输出的jar myapp-api.jar
,这是一个仅用于处理其余API交互的Java项目。它取决于Android.jar因此需要使用apply plugin: 'com.android.application'
而不仅仅是apply plugin: 'java'
从myJavaAPIProject调用./gradlew build jar
来构建并生成.jar到myJavaAPIProject/build/libs/myapp-api.jar
的build.gradle
//Even though this is a Java project, we need to apply the android plugin otherwise it cannot find the SDK/android.jar and so cannot compile
apply plugin: 'com.android.application'
dependencies {
//this ensures we have gson.jar and anything else in the /lib folder
compile fileTree(dir: 'lib', include: '*.jar')
}
repositories {
mavenCentral()
}
android{
compileSdkVersion 21
buildToolsVersion "21.0.1"
defaultConfig {
minSdkVersion 10
targetSdkVersion 21
}
sourceSets {
main {
java {
//points to an empty manifest, needed just to get the build to work
manifest.srcFile 'AndroidManifest.xml'
//defined our src dir as it's not the default dir gradle looks for
java.srcDirs = ['src']
}
}
}
//enforce java 7
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_7
targetCompatibility JavaVersion.VERSION_1_7
}
}
//Actually created the .jar file
task jar(type: Jar) {
//from android.sourceSets.main.java
from 'build/intermediates/classes/release/'
archiveName 'myapp-api.jar'
}
的AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?>
<!-- this is a dummy file needed to ensure gradle validates and builds ok -->
<manifest
package="com.myapp.android"
/>