Java
gradle

Gradle4.9で依存ライブラリを含む単一で実行可能なjarを生成する

メモ


問題

今までこれを使ってオールインワンのJARを生成していた。


しかしGradleを4.9にしたら依存先ファイルが入っていないJarが出来上がるようになった。

compileをimplementationにしたりしたので、

from configurations.compile.collect { it.isDirectory() ? it : zipTree(it) }

という記述を

from configurations.implementation.collect { it.isDirectory() ? it : zipTree(it) }

に変えたところ、次のように怒られるようになった

C:\~~>gradlew

FAILURE: Build failed with an exception.

* Where:
Build file 'C:\~~\build.gradle' line: 129

* What went wrong:
A problem occurred evaluating root project '~'.
> Resolving configuration 'implementation' directly is not allowed

* Try:
Run with --stacktrace option to get the stack trace. Run with --info or --debug option to get more log output. Run with --scan to get full insights.

* Get more help at https://help.gradle.org

BUILD FAILED in 0s

なお名前が間違っている場合は

> Configuration with name ':api' not found.

のように言われるので、明確に内部でブロッキングされているようだ。

エラー文で探してもIssueしか出てこなかったので調べた。


ここにGradle3.3から Configuration.isCanBeResolved() が追加されたとある。

つまりConfigurationごとにcollectできるか否かが違うと。


なので解決可能なConfigurationの中から依存先Jarの一覧が得られないか探してみた。

ここによると configurations はCollectionだそうなので、次のコードで1個1個調べた。

configurations.stream().forEach {

println "################### " + it
if (it.canBeResolved) {
it.collect {
println it.isDirectory() ? it : zipTree(it)
}
}
}


得られたConfigurationの一覧

configuration ':annotationProcessor'

configuration ':api'
configuration ':apiElements'
configuration ':archives'
configuration ':compile'
configuration ':compileClasspath'
configuration ':compileOnly'
configuration ':default'
configuration ':implementation'
configuration ':junitPlatform'
configuration ':runtime'
configuration ':runtimeClasspath'
configuration ':runtimeElements'
configuration ':runtimeOnly'
configuration ':testAnnotationProcessor'
configuration ':testCompile'
configuration ':testCompileClasspath'
configuration ':testCompileOnly'
configuration ':testImplementation'
configuration ':testRuntime'
configuration ':testRuntimeClasspath'
configuration ':testRuntimeOnly'

このうち、 compileClasspath がなんかそれっぽい気がしたので、これを使ってみる。


結論

結果、次のコードで以前のように依存先が全部入ったJarが出来上がった。

from configurations.compileClasspath.collect { it.isDirectory() ? it : zipTree(it) }