Reputation: 2248
I'm writing a simple Gradle task that should take all the intermediate classes and package them inside a .jar
file, the task is inserted in a chain of gradle tasks that are used to build an Android library.
Please note that the Android library is not packaged in a *.aar
archive, I have a few task that will build the jar, build a few shared object and place them in a directory.
The task I wrote so far is the following:
task createDevJarRelease(type: Jar) {
from 'build/intermediates/classes/release'
manifest {
attributes 'Implementation-Title': 'MYJar library',
'Implementation-Version': '1.0'
}
archiveName "my-jar.jar"
doLast {
// Copy the jar in the target directory.
copy {
include "my-jar.jar"
from "build/libs/"
into "targetDir"
}
}
}
What happens is that the jar is properly created and placed in my targetDir
BUT I won't be able to actually use it inside an android project, because the jar
file contains, together with my classes, also other classes from android dependencies that causes clashes when included inside an Android application.
I went inside the build/intermediates/classes/release
and noticed the following directory hierarchy:
build/intermediates/classes/release
|_ android
| |_ arch
| | |_ core
| | |_ ...
| | |_ lifecycle
| | |_ ...
| |_ support
| |_ ...
| | |_ ...
| |_ ...
|_ my
|_ package
|_ name
|_ foo.class
|_ bar.class
I've tried different solutions found online in order to exclude the classes beneath the android
directory but with no success.
I tried explicitly adding the exclude
command in the Gradle task above but didn't work at all (classes are still there).
exclude 'build/intermediates/classes/release/android'
The error seen when building the Application with this jar
is:
> Task :app:transformDexArchiveWithDexMergerForDebug
Dex: Error converting bytecode to dex:
Cause: com.android.dex.DexException: Multiple dex files define Landroid/arch/lifecycle/R;
UNEXPECTED TOP-LEVEL EXCEPTION:
com.android.dex.DexException: Multiple dex files define Landroid/arch/lifecycle/R;
com.android.dex.DexException: Multiple dex files define Landroid/arch/lifecycle/R;
at com.android.dx.merge.DexMerger.readSortableTypes(DexMerger.java:661)
at com.android.dx.merge.DexMerger.getSortedTypes(DexMerger.java:616)
at com.android.dx.merge.DexMerger.mergeClassDefs(DexMerger.java:598)
at com.android.dx.merge.DexMerger.mergeDexes(DexMerger.java:171)
at com.android.dx.merge.DexMerger.merge(DexMerger.java:198)
at com.android.builder.dexing.DexArchiveMergerCallable.call(DexArchiveMergerCallable.java:61)
at com.android.builder.dexing.DexArchiveMergerCallable.call(DexArchiveMergerCallable.java:36)
at java.util.concurrent.ForkJoinTask$AdaptedCallable.exec(ForkJoinTask.java:1424)
at java.util.concurrent.ForkJoinTask.doExec(ForkJoinTask.java:289)
at java.util.concurrent.ForkJoinPool$WorkQueue.runTask(ForkJoinPool.java:1056)
at java.util.concurrent.ForkJoinPool.runWorker(ForkJoinPool.java:1692)
at java.util.concurrent.ForkJoinWorkerThread.run(ForkJoinWorkerThread.java:157)
FAILURE: Build failed with an exception.
The project dependencies are:
dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
androidTestImplementation('com.android.support.test.espresso:espresso-core:2.2.2', {
exclude group: 'com.android.support', module: 'support-annotations'
})
implementation 'com.android.support:appcompat-v7:27.1.1'
testImplementation 'junit:junit:4.12'
}
Upvotes: 1
Views: 992
Reputation: 2248
The actual solution for this was not to exclude
the classes in the jar
gradle task but to change the dependencies of the project, using compileOnly
instead of implementation
when setting the com.android.support
dependency.
The fix is:
dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
androidTestImplementation('com.android.support.test.espresso:espresso-core:2.2.2', {
exclude group: 'com.android.support', module: 'support-annotations'
})
compileOnly 'com.android.support:appcompat-v7:27.1.1'
testImplementation 'junit:junit:4.12'
}
Upvotes: 1