可以将文章内容翻译成中文,广告屏蔽插件可能会导致该功能失效(如失效,请关闭广告屏蔽插件后再试):
问题:
I have a multiproject build and I put a task to build a fat jar in one of the subprojects. I created the task similar to the one described in the cookbook.
jar {
from configurations.compile.collect { it.isDirectory() ? it : zipTree(it) }
manifest { attributes \'Main-Class\': \'com.benmccann.gradle.test.WebServer\' }
}
Running it results in the following error:
Cause: You can\'t change a
configuration which is not in
unresolved state!
I\'m not sure what this error means. I also reported this on the Gradle JIRA in case it is a bug.
回答1:
I posted a solution in JIRA against Gradle:
// Include dependent libraries in archive.
mainClassName = \"com.company.application.Main\"
jar {
manifest {
attributes \"Main-Class\": \"$mainClassName\"
}
from {
configurations.compile.collect { it.isDirectory() ? it : zipTree(it) }
}
}
回答2:
If you want the jar
task to behave normally and a additinal fatJar
task, use the following:
task fatJar(type: Jar) {
classifier = \'all\'
from { configurations.compile.collect { it.isDirectory() ? it : zipTree(it) } }
with jar
}
The important part is with jar
. Without it, the classes of this project are not included.
回答3:
The answer by @felix almost brought me there. I had two issues:
- With Gradle 1.5, the manifest tag was not recognised inside the fatJar task, so the Main-Class attribute could not directly be set
- the jar had conflicting external META-INF files.
The following setup resolves this
jar {
manifest {
attributes(
\'Main-Class\': \'my.project.main\',
)
}
}
task fatJar(type: Jar) {
manifest.from jar.manifest
classifier = \'all\'
from {
configurations.runtimeClasspath.collect { it.isDirectory() ? it : zipTree(it) }
} {
exclude \"META-INF/*.SF\"
exclude \"META-INF/*.DSA\"
exclude \"META-INF/*.RSA\"
}
with jar
}
To add this to the standard assemble or build task, add:
artifacts {
archives fatJar
}
Edit: thanks to @mjaggard: in recent versions of Gradle, change configurations.runtime
to configurations.runtimeClasspath
回答4:
This works fine for me.
My Main class:
package com.curso.online.gradle;
import org.apache.commons.lang3.StringUtils;
import org.apache.log4j.Logger;
public class Main {
public static void main(String[] args) {
Logger logger = Logger.getLogger(Main.class);
logger.debug(\"Starting demo\");
String s = \"Some Value\";
if (!StringUtils.isEmpty(s)) {
System.out.println(\"Welcome \");
}
logger.debug(\"End of demo\");
}
}
And it is the content of my file build.gradle:
apply plugin: \'java\'
apply plugin: \'eclipse\'
repositories {
mavenCentral()
}
dependencies {
compile group: \'commons-collections\', name: \'commons-collections\', version: \'3.2\'
testCompile group: \'junit\', name: \'junit\', version: \'4.+\'
compile \'org.apache.commons:commons-lang3:3.0\'
compile \'log4j:log4j:1.2.16\'
}
task fatJar(type: Jar) {
manifest {
attributes \'Main-Class\': \'com.curso.online.gradle.Main\'
}
baseName = project.name + \'-all\'
from { configurations.compile.collect { it.isDirectory() ? it : zipTree(it) } }
with jar
}
And I write the following in my console:
java -jar ProyectoEclipseTest-all.jar
And the output is great:
log4j:WARN No appenders could be found for logger (com.curso.online.gradle.Main)
.
log4j:WARN Please initialize the log4j system properly.
log4j:WARN See http://logging.apache.org/log4j/1.2/faq.html#noconfig for more in
fo.
Welcome
回答5:
To generate a fat JAR with a main executable class, avoiding problems with signed JARs, I suggest gradle-one-jar plugin. A simple plugin that uses the One-JAR project.
Easy to use:
apply plugin: \'gradle-one-jar\'
buildscript {
repositories {
mavenCentral()
}
dependencies {
classpath \'com.github.rholder:gradle-one-jar:1.0.4\'
}
}
task myjar(type: OneJar) {
mainClass = \'com.benmccann.gradle.test.WebServer\'
}
回答6:
Simple sulution
jar {
manifest {
attributes \'Main-Class\': \'cova2.Main\'
}
doFirst {
from { configurations.runtime.collect { it.isDirectory() ? it : zipTree(it) } }
}
}
回答7:
The answer from @ben almost works for me except that my dependencies are too big and I got the following error
Execution failed for task \':jar\'.
> archive contains more than 65535 entries.
To build this archive, please enable the zip64 extension.
To fix this problem, I have to use the following code
mainClassName = \"com.company.application.Main\"
jar {
manifest {
attributes \"Main-Class\": \"$mainClassName\"
}
zip64 = true
from {
configurations.compile.collect { it.isDirectory() ? it : zipTree(it) }
}
}
回答8:
If you\'re used to ant then you could try the same with Gradle too:
task bundlemyjava{
ant.jar(destfile: \"build/cookmyjar.jar\"){
fileset(dir:\"path to your source\", includes:\'**/*.class,*.class\', excludes:\'if any\')
}
}