如何使用Maven创建具有依赖性的可执行JAR ?

时间:2022-09-03 23:01:17

I want to package my project in a single executable JAR for distribution.

我想将我的项目打包在一个可执行的JAR中进行分发。

How can I make a Maven project package all dependency JARs into my output JAR?

如何使Maven项目将所有依赖项JAR打包到我的输出JAR中?

33 个解决方案

#1


1834  

<build>
  <plugins>
    <plugin>
      <artifactId>maven-assembly-plugin</artifactId>
      <configuration>
        <archive>
          <manifest>
            <mainClass>fully.qualified.MainClass</mainClass>
          </manifest>
        </archive>
        <descriptorRefs>
          <descriptorRef>jar-with-dependencies</descriptorRef>
        </descriptorRefs>
      </configuration>
    </plugin>
  </plugins>
</build>

and you run it with

你运行它

mvn clean compile assembly:single

Compile goal should be added before assembly:single or otherwise the code on your own project is not included.

应该在汇编之前添加Compile目标:不包含您自己项目上的代码。

See more details in comments.

请参阅注释中的更多细节。


Commonly this goal is tied to a build phase to execute automatically. This ensures the JAR is built when executing mvn install or performing a deployment/release.

通常,这个目标被绑定到一个构建阶段,以自动执行。这确保在执行mvn安装或执行部署/发布时构建JAR。

<plugin>
  <artifactId>maven-assembly-plugin</artifactId>
  <configuration>
    <archive>
      <manifest>
        <mainClass>fully.qualified.MainClass</mainClass>
      </manifest>
    </archive>
    <descriptorRefs>
      <descriptorRef>jar-with-dependencies</descriptorRef>
    </descriptorRefs>
  </configuration>
  <executions>
    <execution>
      <id>make-assembly</id> <!-- this is used for inheritance merges -->
      <phase>package</phase> <!-- bind to the packaging phase -->
      <goals>
        <goal>single</goal>
      </goals>
    </execution>
  </executions>
</plugin>

#2


293  

You can use the dependency-plugin to generate all dependencies in a separate directory before the package phase and then include that in the classpath of the manifest:

您可以使用dependency-plugin -plugin在包阶段之前在一个单独的目录中生成所有依赖关系,然后将其包含在manifest的类路径中:

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-dependency-plugin</artifactId>
    <executions>
        <execution>
            <id>copy-dependencies</id>
            <phase>prepare-package</phase>
            <goals>
                <goal>copy-dependencies</goal>
            </goals>
            <configuration>
                <outputDirectory>${project.build.directory}/lib</outputDirectory>
                <overWriteReleases>false</overWriteReleases>
                <overWriteSnapshots>false</overWriteSnapshots>
                <overWriteIfNewer>true</overWriteIfNewer>
            </configuration>
        </execution>
    </executions>
</plugin>
<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-jar-plugin</artifactId>
    <configuration>
        <archive>
            <manifest>
                <addClasspath>true</addClasspath>
                <classpathPrefix>lib/</classpathPrefix>
                <mainClass>theMainClass</mainClass>
            </manifest>
        </archive>
    </configuration>
</plugin>

Alternatively use ${project.build.directory}/classes/lib as OutputDirectory to integrate all jar-files into the main jar, but then you will need to add custom classloading code to load the jars.

或者使用$ { project.build。目录}/class /lib作为OutputDirectory来将所有jar文件集成到主jar中,然后需要添加自定义的类加载代码来加载jar。

#3


130  

I blogged about some different ways to do this.

我写了一些不同的方法。

See Executable Jar with Apache Maven (WordPress)

使用Apache Maven (WordPress)查看可执行Jar

or executable-jar-with-maven-example (GitHub)

或executable-jar-with-maven-example(GitHub)

Notes

Those pros and cons are provided by Stephan.

这些正反观点由Stephan提供。


For Manual Deployment

  • Pros
  • 优点
  • Cons
    • Dependencies are out of the final jar.
    • 依赖项来自最终的jar。
  • 缺点依赖项不在最终jar中。

Copy Dependencies to a specific directory

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-dependency-plugin</artifactId>
  <executions>
    <execution>
      <id>copy-dependencies</id>
      <phase>prepare-package</phase>
      <goals>
        <goal>copy-dependencies</goal>
      </goals>
      <configuration>
        <outputDirectory>${project.build.directory}/${project.build.finalName}.lib</outputDirectory>
      </configuration>
    </execution>
  </executions>
</plugin>

Make the Jar Executable and Classpath Aware

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-jar-plugin</artifactId>
  <configuration>
    <archive>
      <manifest>
        <addClasspath>true</addClasspath>
        <classpathPrefix>${project.build.finalName}.lib/</classpathPrefix>
        <mainClass>${fully.qualified.main.class}</mainClass>
      </manifest>
    </archive>
  </configuration>
</plugin>

At this point the jar is actually executable with external classpath elements.

此时,jar实际上可以与外部类路径元素一起执行。

$ java -jar target/${project.build.finalName}.jar

Make Deployable Archives

The jar file is only executable with the sibling ...lib/ directory. We need to make archives to deploy with the directory and its content.

jar文件只有兄弟级才能执行……lib /目录中。我们需要使归档文件与目录及其内容一起部署。

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-antrun-plugin</artifactId>
  <executions>
    <execution>
      <id>antrun-archive</id>
      <phase>package</phase>
      <goals>
        <goal>run</goal>
      </goals>
      <configuration>
        <target>
          <property name="final.name" value="${project.build.directory}/${project.build.finalName}"/>
          <property name="archive.includes" value="${project.build.finalName}.${project.packaging} ${project.build.finalName}.lib/*"/>
          <property name="tar.destfile" value="${final.name}.tar"/>
          <zip basedir="${project.build.directory}" destfile="${final.name}.zip" includes="${archive.includes}" />
          <tar basedir="${project.build.directory}" destfile="${tar.destfile}" includes="${archive.includes}" />
          <gzip src="${tar.destfile}" destfile="${tar.destfile}.gz" />
          <bzip2 src="${tar.destfile}" destfile="${tar.destfile}.bz2" />
        </target>
      </configuration>
    </execution>
  </executions>
</plugin>

Now you have target/${project.build.finalName}.(zip|tar|tar.bz2|tar.gz) which each contains the jar and lib/*.

现在您有了target/${project.build.finalName}.(zip|tar| .bz2|tar.gz),每个都包含jar和lib/*。


Apache Maven Assembly Plugin

  • Pros
  • 优点
  • Cons
    • No class relocation support (use maven-shade-plugin if class relocation is needed).
    • 不支持类重定位(如果需要类重定位,请使用maven-shade-plugin)。
  • 缺点:不支持类重定位(如果需要类重定位,请使用maven-shade-plugin)。
<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-assembly-plugin</artifactId>
  <executions>
    <execution>
      <phase>package</phase>
      <goals>
        <goal>single</goal>
      </goals>
      <configuration>
        <archive>
          <manifest>
            <mainClass>${fully.qualified.main.class}</mainClass>
          </manifest>
        </archive>
        <descriptorRefs>
          <descriptorRef>jar-with-dependencies</descriptorRef>
        </descriptorRefs>
      </configuration>
    </execution>
  </executions>
</plugin>

You have target/${project.bulid.finalName}-jar-with-dependencies.jar.

你有目标/ $ { project.bulid.finalName } -jar-with-dependencies.jar。


Apache Maven Shade Plugin

  • Pros
  • 优点
  • Cons
  • 缺点
<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-shade-plugin</artifactId>
  <executions>
    <execution>
      <goals>
        <goal>shade</goal>
      </goals>
      <configuration>
        <shadedArtifactAttached>true</shadedArtifactAttached>
        <transformers>
          <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
            <mainClass>${fully.qualified.main.class}</mainClass>
          </transformer>
        </transformers>
      </configuration>
    </execution>
  </executions>
</plugin>

You have target/${project.build.finalName}-shaded.jar.

你有目标/ $ { project.build.finalName } -shaded.jar。


onejar-maven-plugin

  • Pros
  • 优点
  • Cons
    • Not actively supported since 2012.
    • 自2012年以来,并没有得到积极的支持。
  • 自2012年以来,反对意见一直没有得到积极支持。
<plugin>
  <!--groupId>org.dstovall</groupId--> <!-- not available on the central -->
  <groupId>com.jolira</groupId>
  <artifactId>onejar-maven-plugin</artifactId>
  <executions>
    <execution>
      <configuration>
        <mainClass>${fully.qualified.main.class}</mainClass>
        <attachToBuild>true</attachToBuild>
        <!-- https://code.google.com/p/onejar-maven-plugin/issues/detail?id=8 -->
        <!--classifier>onejar</classifier-->
        <filename>${project.build.finalName}-onejar.${project.packaging}</filename>
      </configuration>
      <goals>
        <goal>one-jar</goal>
      </goals>
    </execution>
  </executions>
</plugin>

Spring Boot Maven Plugin

  • Pros
  • 优点
  • Cons
    • Add potential unecessary Spring and Spring Boot related classes.
    • 添加潜在的unecessary Spring和Spring引导相关类。
  • 缺点是增加了潜在的非ecessary Spring和Spring引导相关类。
<plugin>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-maven-plugin</artifactId>
  <executions>
    <execution>
      <goals>
        <goal>repackage</goal>
      </goals>
      <configuration>
        <classifier>spring-boot</classifier>
        <mainClass>${fully.qualified.main.class}</mainClass>
      </configuration>
    </execution>
  </executions>
</plugin>

You have target/${project.bulid.finalName}-spring-boot.jar.

你有目标/ $ { project.bulid.finalName } -spring-boot.jar。

#4


121  

Taking Unanswered's answer and reformatting it, we have:

我们得到了尚未回答的答案,并将其重新格式化:

<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-jar-plugin</artifactId>
            <configuration>
                <archive>
                    <manifest>
                        <addClasspath>true</addClasspath>
                        <mainClass>fully.qualified.MainClass</mainClass>
                    </manifest>
                </archive>
            </configuration>
        </plugin>
        <plugin>
            <artifactId>maven-assembly-plugin</artifactId>
            <configuration>
                <descriptorRefs>
                    <descriptorRef>jar-with-dependencies</descriptorRef>
                </descriptorRefs>
            </configuration>
        </plugin>
    </plugins>
</build>

Next, I would recommend making this a natural part of your build, rather than something to call explicitly. To make this a integral part of your build, add this plugin to your pom.xml and bind it to the package lifecycle event. However, a gotcha is that you need to call the assembly:single goal if putting this in your pom.xml, while you would call 'assembly:assembly' if executing it manually from the command line.

接下来,我建议将此作为构建的自然部分,而不是显式地调用。要使它成为构建的一个组成部分,请将这个插件添加到pom中。xml并将其绑定到包生命周期事件。但是,有一个问题是,您需要调用程序集:如果将其放入您的pom中,则需要单个目标。如果从命令行手动执行,您将调用'assembly:assembly'。

<project>
  [...]
  <build>
      <plugins>
          <plugin>
              <artifactId>maven-assembly-plugin</artifactId>
              <configuration>
                  <archive>
                      <manifest>
                          <addClasspath>true</addClasspath>
                          <mainClass>fully.qualified.MainClass</mainClass>
                      </manifest>
                  </archive>
                  <descriptorRefs>
                      <descriptorRef>jar-with-dependencies</descriptorRef>
                  </descriptorRefs>
              </configuration>
              <executions>
                  <execution>
                      <id>make-my-jar-with-dependencies</id>
                      <phase>package</phase>
                      <goals>
                          <goal>single</goal>
                      </goals>
                  </execution>
              </executions>
          </plugin>
      [...]
      </plugins>
    [...]
  </build>
</project>

#5


91  

Use the maven-shade-plugin to package all dependencies into one uber-jar. It can also be used to build an executable jar by specifying the main class. After trying to use maven-assembly and maven-jar , I found that this plugin best suited my needs.

使用maven-shade-plugin将所有依赖项打包到一个uber-jar中。还可以通过指定主类来构建可执行jar。在尝试使用maven-assembly和maven-jar之后,我发现这个插件最适合我的需要。

I found this plugin particularly useful as it merges content of specific files instead of overwriting them. This is needed when there are resource files that are have the same name across the jars and the plugin tries to package all the resource files

我发现这个插件特别有用,因为它可以合并特定文件的内容,而不是覆盖它们。当有资源文件跨jar具有相同的名称,并且插件试图打包所有资源文件时,就需要这样做

See example below

请参见下面的例子

      <plugins>
    <!-- This plugin provides the capability to package the artifact in an uber-jar, including its dependencies and to shade - i.e. rename - the packages of some of the dependencies. -->
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-shade-plugin</artifactId>
            <version>1.4</version>
            <executions>
                <execution>
                    <phase>package</phase>
                    <goals>
                        <goal>shade</goal>
                    </goals>
                    <configuration>
                        <artifactSet>
                        <!-- signed jars-->
                            <excludes>
                                <exclude>bouncycastle:bcprov-jdk15</exclude>
                            </excludes>
                        </artifactSet>

                         <transformers>
                            <transformer
                                implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
                                <!-- Main class -->
                                <mainClass>com.main.MyMainClass</mainClass>
                            </transformer>
                            <!-- Use resource transformers to prevent file overwrites -->
                            <transformer 
                                 implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                                <resource>properties.properties</resource>
                            </transformer>
                            <transformer
                                implementation="org.apache.maven.plugins.shade.resource.XmlAppendingTransformer">
                                <resource>applicationContext.xml</resource>
                            </transformer>
                            <transformer
                                implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                                <resource>META-INF/cxf/cxf.extension</resource>
                            </transformer>
                            <transformer
                                implementation="org.apache.maven.plugins.shade.resource.XmlAppendingTransformer">
                                <resource>META-INF/cxf/bus-extensions.xml</resource>
                            </transformer>
                     </transformers>
                    </configuration>
                </execution>
            </executions>
        </plugin>

    </plugins>

#6


15  

Long used the maven assembly plugin, but I could not find a solution to the problem with "already added, skipping". Now, I'm using another plugin - onejar-maven-plugin. Example below (mvn package build jar):

长期使用maven程序集插件,但我无法找到“已经添加、跳过”的解决方案。现在,我正在使用另一个插件——onejar-maven-plugin。示例(mvn包构建jar):

<plugin>
    <groupId>org.dstovall</groupId>
    <artifactId>onejar-maven-plugin</artifactId>
    <version>1.3.0</version>
    <executions>
        <execution>
            <configuration>
                <mainClass>com.company.MainClass</mainClass>
            </configuration>
            <goals>
                <goal>one-jar</goal>
            </goals>
        </execution>
    </executions>
</plugin>

You need to add repository for that plugin:

你需要为那个插件添加存储库:

<pluginRepositories>
    <pluginRepository>
        <id>onejar-maven-plugin.googlecode.com</id>
        <url>http://onejar-maven-plugin.googlecode.com/svn/mavenrepo</url>
    </pluginRepository>
</pluginRepositories>

#7


14  

You can use maven-dependency-plugin, but the question was how to create an executable JAR. To do that requires the following alteration to Matthew Franglen's response (btw, using the dependency plugin takes longer to build when starting from a clean target):

您可以使用maven- dependent -plugin,但是问题是如何创建可执行JAR。要做到这一点,需要对Matthew Franglen的响应做如下修改(顺便说一下,使用依赖插件从一个干净的目标开始构建需要花费更长的时间):

<build>
    <plugins>
        <plugin>
            <artifactId>maven-jar-plugin</artifactId>
            <configuration>
                <archive>
                    <manifest>
                        <mainClass>fully.qualified.MainClass</mainClass>
                    </manifest>
                </archive>
            </configuration>
        </plugin>
        <plugin>
            <artifactId>maven-dependency-plugin</artifactId>
            <executions>
                <execution>
                    <id>unpack-dependencies</id>
                    <phase>package</phase>
                    <goals>
                        <goal>unpack-dependencies</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
    </plugins>
    <resources>
        <resource>
            <directory>${basedir}/target/dependency</directory>
        </resource>
    </resources>
</build>

#8


13  

Another option if you really want to repackage the other JARs contents inside your single resultant JAR is the Maven Assembly plugin. It unpacks and then repacks everything into a directory via <unpack>true</unpack>. Then you'd have a second pass that built it into one massive JAR.

如果您真的想重新包装单个结果JAR中的其他JAR内容,另一个选项是Maven程序集插件。它解包,然后通过 true 将所有内容重新打包到一个目录中。然后你会有第二次传球,把它放进一个巨大的罐子里。

Another option is the OneJar plugin. This performs the above repackaging actions all in one step.

另一个选择是OneJar插件。这一步将执行上述重新打包操作。

#9


11  

You can add the following to your pom.xml:

您可以在您的pom.xml中添加以下内容:

<build>
<defaultGoal>install</defaultGoal>
<plugins>
  <plugin>
    <artifactId>maven-compiler-plugin</artifactId>
    <version>2.3.2</version>
    <configuration>
      <source>1.6</source>
      <target>1.6</target>
    </configuration>
  </plugin>
  <plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-jar-plugin</artifactId>
    <version>2.3.1</version>
    <configuration>
      <archive>
        <manifest>
          <addClasspath>true</addClasspath>
          <mainClass>com.mycompany.package.MainClass</mainClass>
        </manifest>
      </archive>
    </configuration>
  </plugin>
  <plugin>
    <artifactId>maven-assembly-plugin</artifactId>
    <configuration>
      <descriptorRefs>
        <descriptorRef>jar-with-dependencies</descriptorRef>
      </descriptorRefs>
      <archive>
        <manifest>
          <mainClass>com.mycompany.package.MainClass</mainClass>
        </manifest>
      </archive>
    </configuration>
    <executions>
      <execution>
        <id>make-my-jar-with-dependencies</id>
        <phase>package</phase>
        <goals>
          <goal>single</goal>
        </goals>
      </execution>
    </executions>
  </plugin>
</plugins>
</build>

Afterwards you have to switch via the console to the directory, where the pom.xml is located. Then you have to execute mvn assembly:single and then your executable JAR file with dependencies will be hopefully build. You can check it when switching to the output (target) directory with cd ./target and starting your jar with a command similiar to java -jar mavenproject1-1.0-SNAPSHOT-jar-with-dependencies.jar.

之后,您必须通过控制台切换到pom所在的目录。xml位于。然后,您必须执行mvn程序集:单个,然后您的可执行JAR文件与依赖项将有望构建。您可以在使用cd ./target切换到output (target)目录时检查它,并使用一个与java -jar mavenproject1-1.0- snapshote -jar- dependency .jar类似的命令启动jar。

I tested this with Apache Maven 3.0.3.

我使用Apache Maven 3.0.3测试了这一点。

#10


8  

You could combine the maven-shade-plugin and maven-jar-plugin.

你可以结合maven-shade-plugin和maven-jar-plugin。

  • The maven-shade-plugin packs your classes and all dependencies in a single jar file.
  • maven-shade-plugin将您的类和所有依赖项装入一个jar文件中。
  • Configure the maven-jar-plugin to specify the main class of your executable jar (see Set Up The Classpath, chapter "Make The Jar Executable").
  • 配置maven-jar-plugin来指定可执行jar的主类(请参阅设置类路径,章节“使jar可执行”)。

Example POM configuration for maven-jar-plugin:

maven-jar-plugin的POM配置示例:

        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-jar-plugin</artifactId>
            <version>2.3.2</version>
            <configuration>
                <archive>
                    <manifest>
                        <addClasspath>true</addClasspath>
                        <mainClass>com.example.MyMainClass</mainClass>
                    </manifest>
                </archive>
            </configuration>
        </plugin>

Finally create the executable jar by invoking:

最后通过调用:

mvn clean package shade:shade

#11


8  

I went through every one of these responses looking to make a fat executable jar containing all dependencies and none of them worked right. The answer is the shade plugin, its very easy and straightforward.

我遍历了所有这些响应,希望创建一个包含所有依赖项的可执行胖jar,但没有一个是正确的。答案是shade插件,它既简单又直接。

    <plugin>
      <groupId>org.apache.maven.plugins</groupId>
      <artifactId>maven-shade-plugin</artifactId>
      <version>2.3</version>
      <executions>
         <!-- Run shade goal on package phase -->
        <execution>
        <phase>package</phase>
        <goals>
            <goal>shade</goal>
        </goals>
        <configuration>
          <transformers>
             <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
                <mainClass>path.to.MainClass</mainClass>
             </transformer>
          </transformers>
        </configuration>
          </execution>
      </executions>
    </plugin>

Be aware that your dependencies need to have a scope of compile or runtime for this to work properly.

请注意,您的依赖项需要有一个编译或运行时范围,才能正常工作。

This example came from mkyong.com

这个例子来自于mkyong.com

#12


7  

Ken Liu has it right in my opinion. The maven dependency plugin allows you to expand all the dependencies, which you can then treat as resources. This allows you to include them in the main artifact. The use of the assembly plugin creates a secondary artifact which can be difficult to modify - in my case I wanted to add custom manifest entries. My pom ended up as:

在我看来,刘肯是对的。maven依赖插件允许您扩展所有依赖项,然后您可以将这些依赖项视为资源。这允许您将它们包含在主工件中。程序集插件的使用创建了一个次要工件,这个工件很难修改——在我的例子中,我想添加自定义清单条目。我的pom最后是:

<project>
 ...
 <build>
  <plugins>
   <plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-dependency-plugin</artifactId>
    <executions>
     <execution>
      <id>unpack-dependencies</id>
      <phase>package</phase>
      <goals>
       <goal>unpack-dependencies</goal>
      </goals>
     </execution>
    </executions>
   </plugin>
  </plugins>
  ...
  <resources>
   <resource>
    <directory>${basedir}/target/dependency</directory>
    <targetPath>/</targetPath>
   </resource>
  </resources>
 </build>
 ...
</project>

#13


6  

Here's an executable jar plugin for Maven that we use at Credit Karma. It creates a jar of jars with a classloader capable of loading classes from nested jars. This allows you to have the same classpath in dev and prod and still keep all classes in a single signed jar file.

这是一个用于Maven的可执行jar插件,我们在Credit Karma上使用它。它创建了一个jar jar,它的类加载器能够从嵌套的jar装载类。这允许您在dev和prod中拥有相同的类路径,并且仍然将所有类保存在一个签名的jar文件中。

https://github.com/creditkarma/maven-exec-jar-plugin

https://github.com/creditkarma/maven-exec-jar-plugin

And here's a blog post with details about the plugin and why we made it: https://engineering.creditkarma.com/general-engineering/new-executable-jar-plugin-available-apache-maven/

这里有一篇博客文章,详细介绍了这个插件,以及我们开发它的原因:https://engineering.creditkarma.com/generalengineering/newexecutablejar -plugin available- apache-mailaven/

#14


5  

Use onejar plugin to build it as one executable jar file which packages all the dependancy jars in it. That solved my problem which was similar to this. When assembly plugin was used, it unpacked all the dependancy jars into source folder and repackage them as a jar, it had over written all the similar implementations I had inside my code which were having the same class names. onejar is an easy solution in here.

使用onejar插件将其构建为一个可执行jar文件,该文件将所有依赖jar打包在其中。这就解决了我的问题。当使用汇编插件时,它将所有依赖jar解压缩到源文件夹中,并将它们重新打包为jar,它覆盖了我代码中所有具有相同类名的类似实现。在这里,onejar是一个简单的解决方案。

#15


5  

Problem with locating shared assembly file with maven-assembly-plugin-2.2.1?

使用maven-assembly-plugin-2.2.1定位共享程序集文件有问题吗?

Try using descriptorId configuration parameter instead of descriptors/descriptor or descriptorRefs/descriptorRef parameters.

尝试使用描述性配置参数,而不是描述符/描述符或描述符引用/描述符引用参数。

Neither of them do what you need: look for the file on classpath. Of course you need adding the package where the shared assembly resides on maven-assembly-plugin's classpath (see below). If you're using Maven 2.x (not Maven 3.x), you may need adding this dependency in top-most parent pom.xml in pluginManagement section.

它们都不做您需要做的事情:在类路径中查找文件。当然,您需要添加共享程序集驻留在maven-assembly-plugin的类路径上的包(参见下面)。如果你使用的是Maven 2。x(不是Maven 3.x),您可能需要在最顶层的父pom中添加这个依赖项。xml pluginManagement节。

See this for more details.

有关更多细节,请参见本文。

Class: org.apache.maven.plugin.assembly.io.DefaultAssemblyReader

类:org.apache.maven.plugin.assembly.io.DefaultAssemblyReader

Example:

例子:

        <!-- Use the assembly plugin to create a zip file of all our dependencies. -->
        <plugin>
            <artifactId>maven-assembly-plugin</artifactId>
            <version>2.2.1</version>
            <executions>
                <execution>
                    <id>make-assembly</id>
                    <phase>package</phase>
                    <goals>
                        <goal>single</goal>
                    </goals>
                    <configuration>
                        <descriptorId>assembly-zip-for-wid</descriptorId>
                    </configuration>
                </execution>
            </executions>
            <dependencies>
                <dependency>
                    <groupId>cz.ness.ct.ip.assemblies</groupId>
                    <artifactId>TEST_SharedAssemblyDescriptor</artifactId>
                    <version>1.0.0-SNAPSHOT</version>
                </dependency>
            </dependencies>
        </plugin>

#16


5  

It should be like that:

应该是这样:

    <plugin>
                <artifactId>maven-dependency-plugin</artifactId>
                <executions>
                        <execution>
                                <id>unpack-dependencies</id>
                                <phase>generate-resources</phase>
                                <goals>
                                        <goal>unpack-dependencies</goal>
                                </goals>
                        </execution>
                </executions>
        </plugin>

Unpacking have to be in generate-resources phase because, if in package phase, will not be included as resources. Try clean package and you'll see.

拆包必须在生成-资源阶段,因为如果在包阶段,将不包含在资源中。试试干净的包装,你就会发现。

#17


4  

I won't answer directly the question as other have already done that before, but I really wonder if it's a good idea to embed all the dependencies in the project's jar itself.

我不会像其他人以前那样直接回答这个问题,但我真的想知道在项目的jar中嵌入所有依赖项是否是个好主意。

I see the point (ease of deployment / usage) but it depends of the use case of your poject (and there may be alternatives (see below)).

我明白这一点(易于部署/使用),但这取决于您的poject的用例(可能还有其他选择(请参见下面)。

If you use it fully standalone, why not.

如果您完全独立地使用它,为什么不呢?

But if you use your project in other contexts (like in a webapp, or dropped in a folder where other jars are sitting), you may have jar duplicates in your classpath (the ones in the folder, the one in the jars). Maybe not a bid deal but i usually avoid this.

但是,如果您在其他上下文中使用项目(比如在webapp中,或者在其他jar所在的文件夹中删除),您可能会在类路径中有jar副本(在文件夹中,在jar中有一个)。也许不是出价,但我通常避免这样。

A good alternative :

一个不错的选择:

  • deploy your application as a .zip / .war : the archive contains your project's jar and all dependent jars ;
  • 将应用程序部署为.zip / .war:存档包含项目的jar和所有依赖的jar;
  • use a dynamic classloader mechanism (see Spring, or you can easily do this yourself) to have a single entry point of your project (a single class to start - see the Manifest mechanism on another answer), which will add (dynamically) to the current classpath all the other needed jars.
  • 使用动态类加载器机制(请参阅Spring,或者您可以自己轻松地这样做)来拥有项目的单个入口点(要启动的单个类——请参阅另一个答案中的Manifest机制),它将(动态地)向当前类路径添加所有其他需要的jar。

Like this, with in the end just a manifest and a "special dynamic classloader main", you can start your project with :

就像这样,最后只有一个清单和一个“特殊的动态类加载器主”,你可以用以下方法开始你的项目:

java -jar ProjectMainJar.jar com.*.projectName.MainDynamicClassLoaderClass

#18


4  

You can use maven-shade plugin to build a uber jar like below

您可以使用maven-shade插件构建一个uber jar,如下所示

        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-shade-plugin</artifactId>
            <executions>
                <execution>
                    <phase>package</phase>
                    <goals>
                        <goal>shade</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>

#19


2  

If you want if from command Line itself . Just run the below command from the project path

如果你想从命令行本身。只需从项目路径运行下面的命令

mvn assembly:assembly

mvn组装:装配

#20


2  

You can also use this plug-in, it is pretty good and I use it for packaging my jars http://sonatype.github.io/jarjar-maven-plugin/

您也可以使用这个插件,它非常好,我使用它来打包我的jar http://sonatype.github.io/jarjar-maven-plugin/

#21


2  

Something that have worked for me was:

对我有用的是:

  <plugin>
    <artifactId>maven-dependency-plugin</artifactId>
    <executions>
      <execution>
        <id>unpack-dependencies</id>
        <phase>prepare-package</phase>
        <goals>
          <goal>unpack-dependencies</goal>
        </goals>
        <configuration>
          <outputDirectory>${project.build.directory}/classes</outputDirectory>
        </configuration>
      </execution>

    </executions>
  </plugin>


  <plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-jar-plugin</artifactId>
    <executions>
      <execution>
        <id>unpack-dependencies</id>
        <phase>package</phase>
      </execution>
    </executions>
    <configuration>
      <archive>
        <manifest>
          <addClasspath>true</addClasspath>
          <classpathPrefix>lib/</classpathPrefix>
          <mainClass>SimpleKeyLogger</mainClass>
        </manifest>
      </archive>
    </configuration>
  </plugin>

I had extraordinary case because my dependency was system one:

我有特殊的情况,因为我的依赖是系统一:

<dependency>
  ..
  <scope>system</scope>
  <systemPath>${project.basedir}/lib/myjar.jar</systemPath>
</dependency>

I have changed the code provided by @user189057 with changes: 1) maven-dependency-plugin is executed in "prepare-package" phase 2) I am extracting unpacked classess directly to "target/classes"

我已经修改了@user189057提供的代码:1)maven-dependency-plugin is execution in "prepare-package" phase 2) I am extract unpacked ess direct to "target/classes"

#22


2  

I tried the most up-voted answer here, and was able to get the jar runnable. But the program didn't run correctly. I do not know what the reason was. When I try to run from Eclipse, I get a different result but when I run the jar from command-line I get a different result (it crashes with a program-specific runtime error).

我在这里尝试了最多向上投票的答案,并且能够运行jar。但是程序没有正确运行。我不知道原因是什么。当我尝试从Eclipse运行时,会得到不同的结果,但是当我从命令行运行jar时,会得到不同的结果(它会因特定于程序的运行时错误而崩溃)。

I had a similar requirement as the OP just that I had too many (Maven) dependencies for my project. Fortunately, the only solution that worked for me was that using Eclipse. Very simple and very straightforward. This is not a solution to the OP but is a solution for someone who has a similar requirement but with many Maven dependencies,

我有一个类似于OP的需求,只是我的项目有太多(Maven)依赖项。幸运的是,唯一对我有用的解决方案是使用Eclipse。非常简单和直接。这不是OP的一个解决方案,而是一个解决方案,适用于有类似需求但有许多Maven依赖项的人,

1) Just right-click on your project folder (in Eclipse) and select Export

只需右键单击项目文件夹(在Eclipse中)并选择Export

2) Then select Java -> Runnable Jar

2)然后选择Java -> Runnable Jar。

3) You will be asked to choose the location of the jar file

您将被要求选择jar文件的位置。

4) Finally, select the class that has the Main method that you want to run and choose Package dependencies with the Jar file and click Finish

最后,选择具有要运行的主方法的类,并选择Jar文件的包依赖项,然后单击Finish

#23


2  

This is the best way i found:

这是我找到的最好的方法:

  <plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-jar-plugin</artifactId>
    <version>2.4</version>
    <configuration>
      <archive>
        <manifest>
        <addClasspath>true</addClasspath>
        <mainClass>com.myDomain.etc.MainClassName</mainClass>
        <classpathPrefix>dependency-jars/</classpathPrefix>
        </manifest>
      </archive>
    </configuration>
  </plugin>
  <plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-dependency-plugin</artifactId>
    <version>2.5.1</version>
    <executions>
      <execution>
        <id>copy-dependencies</id>
        <phase>package</phase>
        <goals>
            <goal>copy-dependencies</goal>
        </goals>
        <configuration>
            <outputDirectory>
               ${project.build.directory}/dependency-jars/
            </outputDirectory>
        </configuration>
      </execution>
    </executions>
  </plugin>

With this configuration, all dependencies will be located in /dependency-jars. My application has no Main class, just context ones, but one of my dependencies do have a Main class (com.myDomain.etc.MainClassName) that starts the JMX server, and receives a start or a stop parameter. So with this i was able to start my application like this:

使用此配置,所有依赖项都将位于/dependency-jar中。我的应用程序没有主类,只是上下文相关的类,但是我的一个依赖项确实有一个主类(com. mydomain.mainclassname),它启动JMX服务器,并接收一个启动或停止参数。这样我就可以开始我的应用了

java -jar ./lib/TestApp-1.0-SNAPSHOT.jar start

I wait it be useful for you all.

我期待它对你们有用。

#24


2  

To resolve this issue we will use Maven Assembly Plugin that will create the JAR together with its dependency JARs into a single executable JAR file. Just add below plugin configuration in your pom.xml file.

为了解决这个问题,我们将使用Maven程序集插件来创建JAR,并将其依赖项JAR文件创建到一个可执行JAR文件中。只需在pom中添加以下插件配置。xml文件。

<build>
   <pluginManagement>
      <plugins>
         <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-assembly-plugin</artifactId>
            <configuration>
               <archive>
                  <manifest>
                     <addClasspath>true</addClasspath>
                     <mainClass>com.your.package.MainClass</mainClass>
                  </manifest>
               </archive>
               <descriptorRefs>
                  <descriptorRef>jar-with-dependencies</descriptorRef>
               </descriptorRefs>
            </configuration>
            <executions>
               <execution>
                  <id>make-my-jar-with-dependencies</id>
                  <phase>package</phase>
                  <goals>
                     <goal>single</goal>
                  </goals>
               </execution>
            </executions>
         </plugin>
      </plugins>
   </pluginManagement>
</build>

After doing this don’t forget to run MAVEN tool with this command mvn clean compile assembly:single

完成此操作之后,不要忘记使用这个命令mvn clean编译程序集:single运行MAVEN工具

http://jkoder.com/maven-creating-a-jar-together-with-its-dependency-jars-into-a-single-executable-jar-file/

http://jkoder.com/maven-creating-a-jar-together-with-its-dependency-jars-into-a-single-executable-jar-file/

#25


1  

The maven-assembly-plugin worked great for me. I spent hours with the maven-dependency-plugin and couldn't make it work. The main reason was that I had to define in the configuration section explicitly the artifact items which should be included as it is described in the documentation. There is an example there for the cases when you want to use it like: mvn dependency:copy, where there are not included any artifactItems but it doesn't work.

maven-assembly-plugin -plugin -plugin -plugin -对我来说非常有用。我花了好几个小时在maven- dependent -plugin上,但是没有成功。主要原因是我必须在configuration部分显式地定义应该包含在文档中描述的工件项。当您希望使用它时,这里有一个示例:mvn依赖项:copy,其中没有包含任何artifactItems,但它不起作用。

#26


1  

This could also be an option,You will be able to build your jar file

这也是一个选项,您将能够构建jar文件

<build>
    <plugins>
        <plugin>
            <!-- Build an executable JAR -->
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-jar-plugin</artifactId>
            <version>2.4</version>
            <configuration>
                <archive>
                    <manifest>
                        <addClasspath>true</addClasspath>
                        <classpathPrefix>lib/</classpathPrefix>
                        <mainClass>WordListDriver</mainClass>
                    </manifest>
                </archive>
            </configuration>
        </plugin>
    </plugins>
</build>

#27


1  

I compared the tree plugins mentioned in this post. I generated 2 jars and a directory with all the jars. I compared the results and definitely the maven-shade-plugin is the best. My challenge was that I have multiple spring resources that needed to be merged, as well as jax-rs, and JDBC services. They were all merged properly by the shade plugin in comparison with the maven-assembly-plugin. In which case the spring will fail unless you copy them to your own resources folder and merge them manually one time. Both plugins output the correct dependency tree. I had multiple scopes like test,provide, compile, etc the test and provided were skipped by both plugins. They both produced the same manifest but I was able to consolidate licenses with the shade plugin using their transformer. With the maven-dependency-plugin of course you don't have those problems because the jars are not extracted. But like some other have pointed you need to carry one extra file(s) to work properly. Here is a snip of the pom.xml

我比较了本文中提到的树插件。我生成了两个jar和一个包含所有jar的目录。我比较了结果,当然maven-shade-plugin是最好的。我的挑战是,我有多个需要合并的spring资源,以及jax-rs和JDBC服务。与maven-assembly-plugin -plugin相比,shade插件对它们进行了适当的合并。在这种情况下,spring将失败,除非您将它们复制到您自己的resources文件夹并一次手工合并它们。两个插件都输出正确的依赖树。我有多个范围,如测试、提供、编译等,测试和提供被两个插件跳过。他们都生成了相同的清单,但是我可以使用他们的transformer将许可证与shade插件合并。使用maven-dependency-plugin当然,您不会遇到这些问题,因为jar没有被提取。但是就像有些人指出的那样,你需要多带一个文件才能正常工作。这是润色。xml的一个片段

            <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-dependency-plugin</artifactId>
            <executions>
                <execution>
                    <id>copy-dependencies</id>
                    <phase>prepare-package</phase>
                    <goals>
                        <goal>copy-dependencies</goal>
                    </goals>
                    <configuration>
                        <outputDirectory>${project.build.directory}/lib</outputDirectory>
                        <includeScope>compile</includeScope>
                        <excludeTransitive>true</excludeTransitive>
                        <overWriteReleases>false</overWriteReleases>
                        <overWriteSnapshots>false</overWriteSnapshots>
                        <overWriteIfNewer>true</overWriteIfNewer>
                    </configuration>
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-assembly-plugin</artifactId>
            <version>2.6</version>
            <configuration>
                <archive>
                    <manifest>
                        <addClasspath>true</addClasspath>
                        <mainClass>com.rbccm.itf.cdd.poller.landingzone.LandingZonePoller</mainClass>
                    </manifest>
                </archive>
                <descriptorRefs>
                    <descriptorRef>jar-with-dependencies</descriptorRef>
                </descriptorRefs>
            </configuration>
            <executions>
                <execution>
                    <id>make-my-jar-with-dependencies</id>
                    <phase>package</phase>
                    <goals>
                        <goal>single</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-shade-plugin</artifactId>
            <version>2.4.3</version>
            <configuration>
                <shadedArtifactAttached>false</shadedArtifactAttached>
                <keepDependenciesWithProvidedScope>false</keepDependenciesWithProvidedScope>
                <transformers>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                        <resource>META-INF/services/javax.ws.rs.ext.Providers</resource>
                    </transformer>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                        <resource>META-INF/spring.factories</resource>
                    </transformer>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                        <resource>META-INF/spring.handlers</resource>
                    </transformer>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                        <resource>META-INF/spring.schemas</resource>
                    </transformer>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                        <resource>META-INF/spring.tooling</resource>
                    </transformer>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer"/>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer"/>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.ApacheLicenseResourceTransformer">
                    </transformer>
                </transformers>
            </configuration>
            <executions>
                <execution>
                    <goals>
                        <goal>shade</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>

#28


1  

Add to pom.xml:

添加pom.xml:

  <dependency>
            <groupId>com.jolira</groupId>
            <artifactId>onejar-maven-plugin</artifactId>
            <version>1.4.4</version>
        </dependency>

and

<plugin>
                <groupId>com.jolira</groupId>
                <artifactId>onejar-maven-plugin</artifactId>
                <version>1.4.4</version>
                <executions>
                    <execution>
                        <goals>
                            <goal>one-jar</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>

Thats it. Next mvn package will also create one fat jar additionally, including all dependency jars.

这是它。下一个mvn包还将另外创建一个fat jar,包括所有依赖jar。

#29


0  

This blog post shows another approach with combining the maven-jar and maven-assembly plugins. With the assembly configuration xml from the blog post it can also be controlled if dependencies will be expanded or just be collected in a folder and referenced by a classpath entry in the manifest:

这篇博文展示了另一种结合maven-jar和maven-assembly插件的方法。通过博客文章中的汇编配置xml,还可以控制依赖项是否将被扩展,或者只是在文件夹中收集,并由清单中的类路径条目引用:

The ideal solution is to include the jars in a lib folder and the manifest.mf file of the main jar include all the jars in classpath.

理想的解决方案是将jar包含在lib文件夹和manifest中。主jar的mf文件包括类路径中的所有jar。

And exactly that one is described here: https://caffebig.wordpress.com/2013/04/05/executable-jar-file-with-dependent-jars-using-maven/

这里描述的就是这个:https://咖啡因big.wordpress.com/2013/04/05/executable-jar-file with-dependent-jars-using-maven/

#30


0  

Okay, so this is my solution. I know it's not using the pom.xml file. But I had the problem my programmme compiling and running on Netbeans but it failing when I tried Java -jar MyJarFile.jar. Now, I don't fully understand Maven and I think this why was having trouble getting Netbeans 8.0.2 to include my jar file in a library to put them into a jar file. I was thinking about how I used to use jar files with no Maven in Eclipse.

这就是我的解。我知道它不用pom。xml文件。但是我在Netbeans上编译和运行程序时遇到了问题,但是当我尝试Java -jar MyJarFile.jar时失败了。现在,我还没有完全理解Maven,我认为这就是为什么Netbeans 8.0.2无法将我的jar文件包含到库中,并将其放入jar文件中。我正在考虑如何使用Eclipse中没有Maven的jar文件。

It's Maven that can compile all the dependanices and plugins. Not Netbeans. (If you can get Netbeans and be able to use java .jar to do this please tell me how (^.^)v )

Maven可以编译所有依赖项和插件。不是Netbeans。(如果你能得到Netbeans和能够使用java . jar这样做请告诉我(^。^)v)

[Solved - for Linux] by opening a terminal.

[解决- Linux]通过打开终端。

Then

然后

cd /MyRootDirectoryForMyProject

Next

下一个

mvn org.apache.maven.plugins:maven-compiler-plugin:compile

Next

下一个

mvn install

This will create jar file in the target directory.

这将在目标目录中创建jar文件。

MyJarFile-1.0-jar-with-dependencies.jar

Now

现在

cd target

(You may need to run: chmod +x MyJarFile-1.0-jar-with-dependencies.jar)

(您可能需要运行:chmod +x myjarfile -1.0 jar-with- dependent .jar)

And finally

最后

java -jar MyJarFile-1.0-jar-with-dependencies.jar

Please see

请参阅

https://cwiki.apache.org/confluence/display/MAVEN/LifecyclePhaseNotFoundException

https://cwiki.apache.org/confluence/display/MAVEN/LifecyclePhaseNotFoundException

I'll post this solution in on a couple of other pages with a similar problem. Hopefully I can save somebody from a week of frustration.

我将把这个解决方案发布在其他几个有类似问题的页面上。希望我能把某人从一周的沮丧中拯救出来。

#1


1834  

<build>
  <plugins>
    <plugin>
      <artifactId>maven-assembly-plugin</artifactId>
      <configuration>
        <archive>
          <manifest>
            <mainClass>fully.qualified.MainClass</mainClass>
          </manifest>
        </archive>
        <descriptorRefs>
          <descriptorRef>jar-with-dependencies</descriptorRef>
        </descriptorRefs>
      </configuration>
    </plugin>
  </plugins>
</build>

and you run it with

你运行它

mvn clean compile assembly:single

Compile goal should be added before assembly:single or otherwise the code on your own project is not included.

应该在汇编之前添加Compile目标:不包含您自己项目上的代码。

See more details in comments.

请参阅注释中的更多细节。


Commonly this goal is tied to a build phase to execute automatically. This ensures the JAR is built when executing mvn install or performing a deployment/release.

通常,这个目标被绑定到一个构建阶段,以自动执行。这确保在执行mvn安装或执行部署/发布时构建JAR。

<plugin>
  <artifactId>maven-assembly-plugin</artifactId>
  <configuration>
    <archive>
      <manifest>
        <mainClass>fully.qualified.MainClass</mainClass>
      </manifest>
    </archive>
    <descriptorRefs>
      <descriptorRef>jar-with-dependencies</descriptorRef>
    </descriptorRefs>
  </configuration>
  <executions>
    <execution>
      <id>make-assembly</id> <!-- this is used for inheritance merges -->
      <phase>package</phase> <!-- bind to the packaging phase -->
      <goals>
        <goal>single</goal>
      </goals>
    </execution>
  </executions>
</plugin>

#2


293  

You can use the dependency-plugin to generate all dependencies in a separate directory before the package phase and then include that in the classpath of the manifest:

您可以使用dependency-plugin -plugin在包阶段之前在一个单独的目录中生成所有依赖关系,然后将其包含在manifest的类路径中:

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-dependency-plugin</artifactId>
    <executions>
        <execution>
            <id>copy-dependencies</id>
            <phase>prepare-package</phase>
            <goals>
                <goal>copy-dependencies</goal>
            </goals>
            <configuration>
                <outputDirectory>${project.build.directory}/lib</outputDirectory>
                <overWriteReleases>false</overWriteReleases>
                <overWriteSnapshots>false</overWriteSnapshots>
                <overWriteIfNewer>true</overWriteIfNewer>
            </configuration>
        </execution>
    </executions>
</plugin>
<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-jar-plugin</artifactId>
    <configuration>
        <archive>
            <manifest>
                <addClasspath>true</addClasspath>
                <classpathPrefix>lib/</classpathPrefix>
                <mainClass>theMainClass</mainClass>
            </manifest>
        </archive>
    </configuration>
</plugin>

Alternatively use ${project.build.directory}/classes/lib as OutputDirectory to integrate all jar-files into the main jar, but then you will need to add custom classloading code to load the jars.

或者使用$ { project.build。目录}/class /lib作为OutputDirectory来将所有jar文件集成到主jar中,然后需要添加自定义的类加载代码来加载jar。

#3


130  

I blogged about some different ways to do this.

我写了一些不同的方法。

See Executable Jar with Apache Maven (WordPress)

使用Apache Maven (WordPress)查看可执行Jar

or executable-jar-with-maven-example (GitHub)

或executable-jar-with-maven-example(GitHub)

Notes

Those pros and cons are provided by Stephan.

这些正反观点由Stephan提供。


For Manual Deployment

  • Pros
  • 优点
  • Cons
    • Dependencies are out of the final jar.
    • 依赖项来自最终的jar。
  • 缺点依赖项不在最终jar中。

Copy Dependencies to a specific directory

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-dependency-plugin</artifactId>
  <executions>
    <execution>
      <id>copy-dependencies</id>
      <phase>prepare-package</phase>
      <goals>
        <goal>copy-dependencies</goal>
      </goals>
      <configuration>
        <outputDirectory>${project.build.directory}/${project.build.finalName}.lib</outputDirectory>
      </configuration>
    </execution>
  </executions>
</plugin>

Make the Jar Executable and Classpath Aware

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-jar-plugin</artifactId>
  <configuration>
    <archive>
      <manifest>
        <addClasspath>true</addClasspath>
        <classpathPrefix>${project.build.finalName}.lib/</classpathPrefix>
        <mainClass>${fully.qualified.main.class}</mainClass>
      </manifest>
    </archive>
  </configuration>
</plugin>

At this point the jar is actually executable with external classpath elements.

此时,jar实际上可以与外部类路径元素一起执行。

$ java -jar target/${project.build.finalName}.jar

Make Deployable Archives

The jar file is only executable with the sibling ...lib/ directory. We need to make archives to deploy with the directory and its content.

jar文件只有兄弟级才能执行……lib /目录中。我们需要使归档文件与目录及其内容一起部署。

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-antrun-plugin</artifactId>
  <executions>
    <execution>
      <id>antrun-archive</id>
      <phase>package</phase>
      <goals>
        <goal>run</goal>
      </goals>
      <configuration>
        <target>
          <property name="final.name" value="${project.build.directory}/${project.build.finalName}"/>
          <property name="archive.includes" value="${project.build.finalName}.${project.packaging} ${project.build.finalName}.lib/*"/>
          <property name="tar.destfile" value="${final.name}.tar"/>
          <zip basedir="${project.build.directory}" destfile="${final.name}.zip" includes="${archive.includes}" />
          <tar basedir="${project.build.directory}" destfile="${tar.destfile}" includes="${archive.includes}" />
          <gzip src="${tar.destfile}" destfile="${tar.destfile}.gz" />
          <bzip2 src="${tar.destfile}" destfile="${tar.destfile}.bz2" />
        </target>
      </configuration>
    </execution>
  </executions>
</plugin>

Now you have target/${project.build.finalName}.(zip|tar|tar.bz2|tar.gz) which each contains the jar and lib/*.

现在您有了target/${project.build.finalName}.(zip|tar| .bz2|tar.gz),每个都包含jar和lib/*。


Apache Maven Assembly Plugin

  • Pros
  • 优点
  • Cons
    • No class relocation support (use maven-shade-plugin if class relocation is needed).
    • 不支持类重定位(如果需要类重定位,请使用maven-shade-plugin)。
  • 缺点:不支持类重定位(如果需要类重定位,请使用maven-shade-plugin)。
<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-assembly-plugin</artifactId>
  <executions>
    <execution>
      <phase>package</phase>
      <goals>
        <goal>single</goal>
      </goals>
      <configuration>
        <archive>
          <manifest>
            <mainClass>${fully.qualified.main.class}</mainClass>
          </manifest>
        </archive>
        <descriptorRefs>
          <descriptorRef>jar-with-dependencies</descriptorRef>
        </descriptorRefs>
      </configuration>
    </execution>
  </executions>
</plugin>

You have target/${project.bulid.finalName}-jar-with-dependencies.jar.

你有目标/ $ { project.bulid.finalName } -jar-with-dependencies.jar。


Apache Maven Shade Plugin

  • Pros
  • 优点
  • Cons
  • 缺点
<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-shade-plugin</artifactId>
  <executions>
    <execution>
      <goals>
        <goal>shade</goal>
      </goals>
      <configuration>
        <shadedArtifactAttached>true</shadedArtifactAttached>
        <transformers>
          <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
            <mainClass>${fully.qualified.main.class}</mainClass>
          </transformer>
        </transformers>
      </configuration>
    </execution>
  </executions>
</plugin>

You have target/${project.build.finalName}-shaded.jar.

你有目标/ $ { project.build.finalName } -shaded.jar。


onejar-maven-plugin

  • Pros
  • 优点
  • Cons
    • Not actively supported since 2012.
    • 自2012年以来,并没有得到积极的支持。
  • 自2012年以来,反对意见一直没有得到积极支持。
<plugin>
  <!--groupId>org.dstovall</groupId--> <!-- not available on the central -->
  <groupId>com.jolira</groupId>
  <artifactId>onejar-maven-plugin</artifactId>
  <executions>
    <execution>
      <configuration>
        <mainClass>${fully.qualified.main.class}</mainClass>
        <attachToBuild>true</attachToBuild>
        <!-- https://code.google.com/p/onejar-maven-plugin/issues/detail?id=8 -->
        <!--classifier>onejar</classifier-->
        <filename>${project.build.finalName}-onejar.${project.packaging}</filename>
      </configuration>
      <goals>
        <goal>one-jar</goal>
      </goals>
    </execution>
  </executions>
</plugin>

Spring Boot Maven Plugin

  • Pros
  • 优点
  • Cons
    • Add potential unecessary Spring and Spring Boot related classes.
    • 添加潜在的unecessary Spring和Spring引导相关类。
  • 缺点是增加了潜在的非ecessary Spring和Spring引导相关类。
<plugin>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-maven-plugin</artifactId>
  <executions>
    <execution>
      <goals>
        <goal>repackage</goal>
      </goals>
      <configuration>
        <classifier>spring-boot</classifier>
        <mainClass>${fully.qualified.main.class}</mainClass>
      </configuration>
    </execution>
  </executions>
</plugin>

You have target/${project.bulid.finalName}-spring-boot.jar.

你有目标/ $ { project.bulid.finalName } -spring-boot.jar。

#4


121  

Taking Unanswered's answer and reformatting it, we have:

我们得到了尚未回答的答案,并将其重新格式化:

<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-jar-plugin</artifactId>
            <configuration>
                <archive>
                    <manifest>
                        <addClasspath>true</addClasspath>
                        <mainClass>fully.qualified.MainClass</mainClass>
                    </manifest>
                </archive>
            </configuration>
        </plugin>
        <plugin>
            <artifactId>maven-assembly-plugin</artifactId>
            <configuration>
                <descriptorRefs>
                    <descriptorRef>jar-with-dependencies</descriptorRef>
                </descriptorRefs>
            </configuration>
        </plugin>
    </plugins>
</build>

Next, I would recommend making this a natural part of your build, rather than something to call explicitly. To make this a integral part of your build, add this plugin to your pom.xml and bind it to the package lifecycle event. However, a gotcha is that you need to call the assembly:single goal if putting this in your pom.xml, while you would call 'assembly:assembly' if executing it manually from the command line.

接下来,我建议将此作为构建的自然部分,而不是显式地调用。要使它成为构建的一个组成部分,请将这个插件添加到pom中。xml并将其绑定到包生命周期事件。但是,有一个问题是,您需要调用程序集:如果将其放入您的pom中,则需要单个目标。如果从命令行手动执行,您将调用'assembly:assembly'。

<project>
  [...]
  <build>
      <plugins>
          <plugin>
              <artifactId>maven-assembly-plugin</artifactId>
              <configuration>
                  <archive>
                      <manifest>
                          <addClasspath>true</addClasspath>
                          <mainClass>fully.qualified.MainClass</mainClass>
                      </manifest>
                  </archive>
                  <descriptorRefs>
                      <descriptorRef>jar-with-dependencies</descriptorRef>
                  </descriptorRefs>
              </configuration>
              <executions>
                  <execution>
                      <id>make-my-jar-with-dependencies</id>
                      <phase>package</phase>
                      <goals>
                          <goal>single</goal>
                      </goals>
                  </execution>
              </executions>
          </plugin>
      [...]
      </plugins>
    [...]
  </build>
</project>

#5


91  

Use the maven-shade-plugin to package all dependencies into one uber-jar. It can also be used to build an executable jar by specifying the main class. After trying to use maven-assembly and maven-jar , I found that this plugin best suited my needs.

使用maven-shade-plugin将所有依赖项打包到一个uber-jar中。还可以通过指定主类来构建可执行jar。在尝试使用maven-assembly和maven-jar之后,我发现这个插件最适合我的需要。

I found this plugin particularly useful as it merges content of specific files instead of overwriting them. This is needed when there are resource files that are have the same name across the jars and the plugin tries to package all the resource files

我发现这个插件特别有用,因为它可以合并特定文件的内容,而不是覆盖它们。当有资源文件跨jar具有相同的名称,并且插件试图打包所有资源文件时,就需要这样做

See example below

请参见下面的例子

      <plugins>
    <!-- This plugin provides the capability to package the artifact in an uber-jar, including its dependencies and to shade - i.e. rename - the packages of some of the dependencies. -->
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-shade-plugin</artifactId>
            <version>1.4</version>
            <executions>
                <execution>
                    <phase>package</phase>
                    <goals>
                        <goal>shade</goal>
                    </goals>
                    <configuration>
                        <artifactSet>
                        <!-- signed jars-->
                            <excludes>
                                <exclude>bouncycastle:bcprov-jdk15</exclude>
                            </excludes>
                        </artifactSet>

                         <transformers>
                            <transformer
                                implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
                                <!-- Main class -->
                                <mainClass>com.main.MyMainClass</mainClass>
                            </transformer>
                            <!-- Use resource transformers to prevent file overwrites -->
                            <transformer 
                                 implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                                <resource>properties.properties</resource>
                            </transformer>
                            <transformer
                                implementation="org.apache.maven.plugins.shade.resource.XmlAppendingTransformer">
                                <resource>applicationContext.xml</resource>
                            </transformer>
                            <transformer
                                implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                                <resource>META-INF/cxf/cxf.extension</resource>
                            </transformer>
                            <transformer
                                implementation="org.apache.maven.plugins.shade.resource.XmlAppendingTransformer">
                                <resource>META-INF/cxf/bus-extensions.xml</resource>
                            </transformer>
                     </transformers>
                    </configuration>
                </execution>
            </executions>
        </plugin>

    </plugins>

#6


15  

Long used the maven assembly plugin, but I could not find a solution to the problem with "already added, skipping". Now, I'm using another plugin - onejar-maven-plugin. Example below (mvn package build jar):

长期使用maven程序集插件,但我无法找到“已经添加、跳过”的解决方案。现在,我正在使用另一个插件——onejar-maven-plugin。示例(mvn包构建jar):

<plugin>
    <groupId>org.dstovall</groupId>
    <artifactId>onejar-maven-plugin</artifactId>
    <version>1.3.0</version>
    <executions>
        <execution>
            <configuration>
                <mainClass>com.company.MainClass</mainClass>
            </configuration>
            <goals>
                <goal>one-jar</goal>
            </goals>
        </execution>
    </executions>
</plugin>

You need to add repository for that plugin:

你需要为那个插件添加存储库:

<pluginRepositories>
    <pluginRepository>
        <id>onejar-maven-plugin.googlecode.com</id>
        <url>http://onejar-maven-plugin.googlecode.com/svn/mavenrepo</url>
    </pluginRepository>
</pluginRepositories>

#7


14  

You can use maven-dependency-plugin, but the question was how to create an executable JAR. To do that requires the following alteration to Matthew Franglen's response (btw, using the dependency plugin takes longer to build when starting from a clean target):

您可以使用maven- dependent -plugin,但是问题是如何创建可执行JAR。要做到这一点,需要对Matthew Franglen的响应做如下修改(顺便说一下,使用依赖插件从一个干净的目标开始构建需要花费更长的时间):

<build>
    <plugins>
        <plugin>
            <artifactId>maven-jar-plugin</artifactId>
            <configuration>
                <archive>
                    <manifest>
                        <mainClass>fully.qualified.MainClass</mainClass>
                    </manifest>
                </archive>
            </configuration>
        </plugin>
        <plugin>
            <artifactId>maven-dependency-plugin</artifactId>
            <executions>
                <execution>
                    <id>unpack-dependencies</id>
                    <phase>package</phase>
                    <goals>
                        <goal>unpack-dependencies</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
    </plugins>
    <resources>
        <resource>
            <directory>${basedir}/target/dependency</directory>
        </resource>
    </resources>
</build>

#8


13  

Another option if you really want to repackage the other JARs contents inside your single resultant JAR is the Maven Assembly plugin. It unpacks and then repacks everything into a directory via <unpack>true</unpack>. Then you'd have a second pass that built it into one massive JAR.

如果您真的想重新包装单个结果JAR中的其他JAR内容,另一个选项是Maven程序集插件。它解包,然后通过 true 将所有内容重新打包到一个目录中。然后你会有第二次传球,把它放进一个巨大的罐子里。

Another option is the OneJar plugin. This performs the above repackaging actions all in one step.

另一个选择是OneJar插件。这一步将执行上述重新打包操作。

#9


11  

You can add the following to your pom.xml:

您可以在您的pom.xml中添加以下内容:

<build>
<defaultGoal>install</defaultGoal>
<plugins>
  <plugin>
    <artifactId>maven-compiler-plugin</artifactId>
    <version>2.3.2</version>
    <configuration>
      <source>1.6</source>
      <target>1.6</target>
    </configuration>
  </plugin>
  <plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-jar-plugin</artifactId>
    <version>2.3.1</version>
    <configuration>
      <archive>
        <manifest>
          <addClasspath>true</addClasspath>
          <mainClass>com.mycompany.package.MainClass</mainClass>
        </manifest>
      </archive>
    </configuration>
  </plugin>
  <plugin>
    <artifactId>maven-assembly-plugin</artifactId>
    <configuration>
      <descriptorRefs>
        <descriptorRef>jar-with-dependencies</descriptorRef>
      </descriptorRefs>
      <archive>
        <manifest>
          <mainClass>com.mycompany.package.MainClass</mainClass>
        </manifest>
      </archive>
    </configuration>
    <executions>
      <execution>
        <id>make-my-jar-with-dependencies</id>
        <phase>package</phase>
        <goals>
          <goal>single</goal>
        </goals>
      </execution>
    </executions>
  </plugin>
</plugins>
</build>

Afterwards you have to switch via the console to the directory, where the pom.xml is located. Then you have to execute mvn assembly:single and then your executable JAR file with dependencies will be hopefully build. You can check it when switching to the output (target) directory with cd ./target and starting your jar with a command similiar to java -jar mavenproject1-1.0-SNAPSHOT-jar-with-dependencies.jar.

之后,您必须通过控制台切换到pom所在的目录。xml位于。然后,您必须执行mvn程序集:单个,然后您的可执行JAR文件与依赖项将有望构建。您可以在使用cd ./target切换到output (target)目录时检查它,并使用一个与java -jar mavenproject1-1.0- snapshote -jar- dependency .jar类似的命令启动jar。

I tested this with Apache Maven 3.0.3.

我使用Apache Maven 3.0.3测试了这一点。

#10


8  

You could combine the maven-shade-plugin and maven-jar-plugin.

你可以结合maven-shade-plugin和maven-jar-plugin。

  • The maven-shade-plugin packs your classes and all dependencies in a single jar file.
  • maven-shade-plugin将您的类和所有依赖项装入一个jar文件中。
  • Configure the maven-jar-plugin to specify the main class of your executable jar (see Set Up The Classpath, chapter "Make The Jar Executable").
  • 配置maven-jar-plugin来指定可执行jar的主类(请参阅设置类路径,章节“使jar可执行”)。

Example POM configuration for maven-jar-plugin:

maven-jar-plugin的POM配置示例:

        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-jar-plugin</artifactId>
            <version>2.3.2</version>
            <configuration>
                <archive>
                    <manifest>
                        <addClasspath>true</addClasspath>
                        <mainClass>com.example.MyMainClass</mainClass>
                    </manifest>
                </archive>
            </configuration>
        </plugin>

Finally create the executable jar by invoking:

最后通过调用:

mvn clean package shade:shade

#11


8  

I went through every one of these responses looking to make a fat executable jar containing all dependencies and none of them worked right. The answer is the shade plugin, its very easy and straightforward.

我遍历了所有这些响应,希望创建一个包含所有依赖项的可执行胖jar,但没有一个是正确的。答案是shade插件,它既简单又直接。

    <plugin>
      <groupId>org.apache.maven.plugins</groupId>
      <artifactId>maven-shade-plugin</artifactId>
      <version>2.3</version>
      <executions>
         <!-- Run shade goal on package phase -->
        <execution>
        <phase>package</phase>
        <goals>
            <goal>shade</goal>
        </goals>
        <configuration>
          <transformers>
             <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
                <mainClass>path.to.MainClass</mainClass>
             </transformer>
          </transformers>
        </configuration>
          </execution>
      </executions>
    </plugin>

Be aware that your dependencies need to have a scope of compile or runtime for this to work properly.

请注意,您的依赖项需要有一个编译或运行时范围,才能正常工作。

This example came from mkyong.com

这个例子来自于mkyong.com

#12


7  

Ken Liu has it right in my opinion. The maven dependency plugin allows you to expand all the dependencies, which you can then treat as resources. This allows you to include them in the main artifact. The use of the assembly plugin creates a secondary artifact which can be difficult to modify - in my case I wanted to add custom manifest entries. My pom ended up as:

在我看来,刘肯是对的。maven依赖插件允许您扩展所有依赖项,然后您可以将这些依赖项视为资源。这允许您将它们包含在主工件中。程序集插件的使用创建了一个次要工件,这个工件很难修改——在我的例子中,我想添加自定义清单条目。我的pom最后是:

<project>
 ...
 <build>
  <plugins>
   <plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-dependency-plugin</artifactId>
    <executions>
     <execution>
      <id>unpack-dependencies</id>
      <phase>package</phase>
      <goals>
       <goal>unpack-dependencies</goal>
      </goals>
     </execution>
    </executions>
   </plugin>
  </plugins>
  ...
  <resources>
   <resource>
    <directory>${basedir}/target/dependency</directory>
    <targetPath>/</targetPath>
   </resource>
  </resources>
 </build>
 ...
</project>

#13


6  

Here's an executable jar plugin for Maven that we use at Credit Karma. It creates a jar of jars with a classloader capable of loading classes from nested jars. This allows you to have the same classpath in dev and prod and still keep all classes in a single signed jar file.

这是一个用于Maven的可执行jar插件,我们在Credit Karma上使用它。它创建了一个jar jar,它的类加载器能够从嵌套的jar装载类。这允许您在dev和prod中拥有相同的类路径,并且仍然将所有类保存在一个签名的jar文件中。

https://github.com/creditkarma/maven-exec-jar-plugin

https://github.com/creditkarma/maven-exec-jar-plugin

And here's a blog post with details about the plugin and why we made it: https://engineering.creditkarma.com/general-engineering/new-executable-jar-plugin-available-apache-maven/

这里有一篇博客文章,详细介绍了这个插件,以及我们开发它的原因:https://engineering.creditkarma.com/generalengineering/newexecutablejar -plugin available- apache-mailaven/

#14


5  

Use onejar plugin to build it as one executable jar file which packages all the dependancy jars in it. That solved my problem which was similar to this. When assembly plugin was used, it unpacked all the dependancy jars into source folder and repackage them as a jar, it had over written all the similar implementations I had inside my code which were having the same class names. onejar is an easy solution in here.

使用onejar插件将其构建为一个可执行jar文件,该文件将所有依赖jar打包在其中。这就解决了我的问题。当使用汇编插件时,它将所有依赖jar解压缩到源文件夹中,并将它们重新打包为jar,它覆盖了我代码中所有具有相同类名的类似实现。在这里,onejar是一个简单的解决方案。

#15


5  

Problem with locating shared assembly file with maven-assembly-plugin-2.2.1?

使用maven-assembly-plugin-2.2.1定位共享程序集文件有问题吗?

Try using descriptorId configuration parameter instead of descriptors/descriptor or descriptorRefs/descriptorRef parameters.

尝试使用描述性配置参数,而不是描述符/描述符或描述符引用/描述符引用参数。

Neither of them do what you need: look for the file on classpath. Of course you need adding the package where the shared assembly resides on maven-assembly-plugin's classpath (see below). If you're using Maven 2.x (not Maven 3.x), you may need adding this dependency in top-most parent pom.xml in pluginManagement section.

它们都不做您需要做的事情:在类路径中查找文件。当然,您需要添加共享程序集驻留在maven-assembly-plugin的类路径上的包(参见下面)。如果你使用的是Maven 2。x(不是Maven 3.x),您可能需要在最顶层的父pom中添加这个依赖项。xml pluginManagement节。

See this for more details.

有关更多细节,请参见本文。

Class: org.apache.maven.plugin.assembly.io.DefaultAssemblyReader

类:org.apache.maven.plugin.assembly.io.DefaultAssemblyReader

Example:

例子:

        <!-- Use the assembly plugin to create a zip file of all our dependencies. -->
        <plugin>
            <artifactId>maven-assembly-plugin</artifactId>
            <version>2.2.1</version>
            <executions>
                <execution>
                    <id>make-assembly</id>
                    <phase>package</phase>
                    <goals>
                        <goal>single</goal>
                    </goals>
                    <configuration>
                        <descriptorId>assembly-zip-for-wid</descriptorId>
                    </configuration>
                </execution>
            </executions>
            <dependencies>
                <dependency>
                    <groupId>cz.ness.ct.ip.assemblies</groupId>
                    <artifactId>TEST_SharedAssemblyDescriptor</artifactId>
                    <version>1.0.0-SNAPSHOT</version>
                </dependency>
            </dependencies>
        </plugin>

#16


5  

It should be like that:

应该是这样:

    <plugin>
                <artifactId>maven-dependency-plugin</artifactId>
                <executions>
                        <execution>
                                <id>unpack-dependencies</id>
                                <phase>generate-resources</phase>
                                <goals>
                                        <goal>unpack-dependencies</goal>
                                </goals>
                        </execution>
                </executions>
        </plugin>

Unpacking have to be in generate-resources phase because, if in package phase, will not be included as resources. Try clean package and you'll see.

拆包必须在生成-资源阶段,因为如果在包阶段,将不包含在资源中。试试干净的包装,你就会发现。

#17


4  

I won't answer directly the question as other have already done that before, but I really wonder if it's a good idea to embed all the dependencies in the project's jar itself.

我不会像其他人以前那样直接回答这个问题,但我真的想知道在项目的jar中嵌入所有依赖项是否是个好主意。

I see the point (ease of deployment / usage) but it depends of the use case of your poject (and there may be alternatives (see below)).

我明白这一点(易于部署/使用),但这取决于您的poject的用例(可能还有其他选择(请参见下面)。

If you use it fully standalone, why not.

如果您完全独立地使用它,为什么不呢?

But if you use your project in other contexts (like in a webapp, or dropped in a folder where other jars are sitting), you may have jar duplicates in your classpath (the ones in the folder, the one in the jars). Maybe not a bid deal but i usually avoid this.

但是,如果您在其他上下文中使用项目(比如在webapp中,或者在其他jar所在的文件夹中删除),您可能会在类路径中有jar副本(在文件夹中,在jar中有一个)。也许不是出价,但我通常避免这样。

A good alternative :

一个不错的选择:

  • deploy your application as a .zip / .war : the archive contains your project's jar and all dependent jars ;
  • 将应用程序部署为.zip / .war:存档包含项目的jar和所有依赖的jar;
  • use a dynamic classloader mechanism (see Spring, or you can easily do this yourself) to have a single entry point of your project (a single class to start - see the Manifest mechanism on another answer), which will add (dynamically) to the current classpath all the other needed jars.
  • 使用动态类加载器机制(请参阅Spring,或者您可以自己轻松地这样做)来拥有项目的单个入口点(要启动的单个类——请参阅另一个答案中的Manifest机制),它将(动态地)向当前类路径添加所有其他需要的jar。

Like this, with in the end just a manifest and a "special dynamic classloader main", you can start your project with :

就像这样,最后只有一个清单和一个“特殊的动态类加载器主”,你可以用以下方法开始你的项目:

java -jar ProjectMainJar.jar com.*.projectName.MainDynamicClassLoaderClass

#18


4  

You can use maven-shade plugin to build a uber jar like below

您可以使用maven-shade插件构建一个uber jar,如下所示

        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-shade-plugin</artifactId>
            <executions>
                <execution>
                    <phase>package</phase>
                    <goals>
                        <goal>shade</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>

#19


2  

If you want if from command Line itself . Just run the below command from the project path

如果你想从命令行本身。只需从项目路径运行下面的命令

mvn assembly:assembly

mvn组装:装配

#20


2  

You can also use this plug-in, it is pretty good and I use it for packaging my jars http://sonatype.github.io/jarjar-maven-plugin/

您也可以使用这个插件,它非常好,我使用它来打包我的jar http://sonatype.github.io/jarjar-maven-plugin/

#21


2  

Something that have worked for me was:

对我有用的是:

  <plugin>
    <artifactId>maven-dependency-plugin</artifactId>
    <executions>
      <execution>
        <id>unpack-dependencies</id>
        <phase>prepare-package</phase>
        <goals>
          <goal>unpack-dependencies</goal>
        </goals>
        <configuration>
          <outputDirectory>${project.build.directory}/classes</outputDirectory>
        </configuration>
      </execution>

    </executions>
  </plugin>


  <plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-jar-plugin</artifactId>
    <executions>
      <execution>
        <id>unpack-dependencies</id>
        <phase>package</phase>
      </execution>
    </executions>
    <configuration>
      <archive>
        <manifest>
          <addClasspath>true</addClasspath>
          <classpathPrefix>lib/</classpathPrefix>
          <mainClass>SimpleKeyLogger</mainClass>
        </manifest>
      </archive>
    </configuration>
  </plugin>

I had extraordinary case because my dependency was system one:

我有特殊的情况,因为我的依赖是系统一:

<dependency>
  ..
  <scope>system</scope>
  <systemPath>${project.basedir}/lib/myjar.jar</systemPath>
</dependency>

I have changed the code provided by @user189057 with changes: 1) maven-dependency-plugin is executed in "prepare-package" phase 2) I am extracting unpacked classess directly to "target/classes"

我已经修改了@user189057提供的代码:1)maven-dependency-plugin is execution in "prepare-package" phase 2) I am extract unpacked ess direct to "target/classes"

#22


2  

I tried the most up-voted answer here, and was able to get the jar runnable. But the program didn't run correctly. I do not know what the reason was. When I try to run from Eclipse, I get a different result but when I run the jar from command-line I get a different result (it crashes with a program-specific runtime error).

我在这里尝试了最多向上投票的答案,并且能够运行jar。但是程序没有正确运行。我不知道原因是什么。当我尝试从Eclipse运行时,会得到不同的结果,但是当我从命令行运行jar时,会得到不同的结果(它会因特定于程序的运行时错误而崩溃)。

I had a similar requirement as the OP just that I had too many (Maven) dependencies for my project. Fortunately, the only solution that worked for me was that using Eclipse. Very simple and very straightforward. This is not a solution to the OP but is a solution for someone who has a similar requirement but with many Maven dependencies,

我有一个类似于OP的需求,只是我的项目有太多(Maven)依赖项。幸运的是,唯一对我有用的解决方案是使用Eclipse。非常简单和直接。这不是OP的一个解决方案,而是一个解决方案,适用于有类似需求但有许多Maven依赖项的人,

1) Just right-click on your project folder (in Eclipse) and select Export

只需右键单击项目文件夹(在Eclipse中)并选择Export

2) Then select Java -> Runnable Jar

2)然后选择Java -> Runnable Jar。

3) You will be asked to choose the location of the jar file

您将被要求选择jar文件的位置。

4) Finally, select the class that has the Main method that you want to run and choose Package dependencies with the Jar file and click Finish

最后,选择具有要运行的主方法的类,并选择Jar文件的包依赖项,然后单击Finish

#23


2  

This is the best way i found:

这是我找到的最好的方法:

  <plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-jar-plugin</artifactId>
    <version>2.4</version>
    <configuration>
      <archive>
        <manifest>
        <addClasspath>true</addClasspath>
        <mainClass>com.myDomain.etc.MainClassName</mainClass>
        <classpathPrefix>dependency-jars/</classpathPrefix>
        </manifest>
      </archive>
    </configuration>
  </plugin>
  <plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-dependency-plugin</artifactId>
    <version>2.5.1</version>
    <executions>
      <execution>
        <id>copy-dependencies</id>
        <phase>package</phase>
        <goals>
            <goal>copy-dependencies</goal>
        </goals>
        <configuration>
            <outputDirectory>
               ${project.build.directory}/dependency-jars/
            </outputDirectory>
        </configuration>
      </execution>
    </executions>
  </plugin>

With this configuration, all dependencies will be located in /dependency-jars. My application has no Main class, just context ones, but one of my dependencies do have a Main class (com.myDomain.etc.MainClassName) that starts the JMX server, and receives a start or a stop parameter. So with this i was able to start my application like this:

使用此配置,所有依赖项都将位于/dependency-jar中。我的应用程序没有主类,只是上下文相关的类,但是我的一个依赖项确实有一个主类(com. mydomain.mainclassname),它启动JMX服务器,并接收一个启动或停止参数。这样我就可以开始我的应用了

java -jar ./lib/TestApp-1.0-SNAPSHOT.jar start

I wait it be useful for you all.

我期待它对你们有用。

#24


2  

To resolve this issue we will use Maven Assembly Plugin that will create the JAR together with its dependency JARs into a single executable JAR file. Just add below plugin configuration in your pom.xml file.

为了解决这个问题,我们将使用Maven程序集插件来创建JAR,并将其依赖项JAR文件创建到一个可执行JAR文件中。只需在pom中添加以下插件配置。xml文件。

<build>
   <pluginManagement>
      <plugins>
         <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-assembly-plugin</artifactId>
            <configuration>
               <archive>
                  <manifest>
                     <addClasspath>true</addClasspath>
                     <mainClass>com.your.package.MainClass</mainClass>
                  </manifest>
               </archive>
               <descriptorRefs>
                  <descriptorRef>jar-with-dependencies</descriptorRef>
               </descriptorRefs>
            </configuration>
            <executions>
               <execution>
                  <id>make-my-jar-with-dependencies</id>
                  <phase>package</phase>
                  <goals>
                     <goal>single</goal>
                  </goals>
               </execution>
            </executions>
         </plugin>
      </plugins>
   </pluginManagement>
</build>

After doing this don’t forget to run MAVEN tool with this command mvn clean compile assembly:single

完成此操作之后,不要忘记使用这个命令mvn clean编译程序集:single运行MAVEN工具

http://jkoder.com/maven-creating-a-jar-together-with-its-dependency-jars-into-a-single-executable-jar-file/

http://jkoder.com/maven-creating-a-jar-together-with-its-dependency-jars-into-a-single-executable-jar-file/

#25


1  

The maven-assembly-plugin worked great for me. I spent hours with the maven-dependency-plugin and couldn't make it work. The main reason was that I had to define in the configuration section explicitly the artifact items which should be included as it is described in the documentation. There is an example there for the cases when you want to use it like: mvn dependency:copy, where there are not included any artifactItems but it doesn't work.

maven-assembly-plugin -plugin -plugin -plugin -对我来说非常有用。我花了好几个小时在maven- dependent -plugin上,但是没有成功。主要原因是我必须在configuration部分显式地定义应该包含在文档中描述的工件项。当您希望使用它时,这里有一个示例:mvn依赖项:copy,其中没有包含任何artifactItems,但它不起作用。

#26


1  

This could also be an option,You will be able to build your jar file

这也是一个选项,您将能够构建jar文件

<build>
    <plugins>
        <plugin>
            <!-- Build an executable JAR -->
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-jar-plugin</artifactId>
            <version>2.4</version>
            <configuration>
                <archive>
                    <manifest>
                        <addClasspath>true</addClasspath>
                        <classpathPrefix>lib/</classpathPrefix>
                        <mainClass>WordListDriver</mainClass>
                    </manifest>
                </archive>
            </configuration>
        </plugin>
    </plugins>
</build>

#27


1  

I compared the tree plugins mentioned in this post. I generated 2 jars and a directory with all the jars. I compared the results and definitely the maven-shade-plugin is the best. My challenge was that I have multiple spring resources that needed to be merged, as well as jax-rs, and JDBC services. They were all merged properly by the shade plugin in comparison with the maven-assembly-plugin. In which case the spring will fail unless you copy them to your own resources folder and merge them manually one time. Both plugins output the correct dependency tree. I had multiple scopes like test,provide, compile, etc the test and provided were skipped by both plugins. They both produced the same manifest but I was able to consolidate licenses with the shade plugin using their transformer. With the maven-dependency-plugin of course you don't have those problems because the jars are not extracted. But like some other have pointed you need to carry one extra file(s) to work properly. Here is a snip of the pom.xml

我比较了本文中提到的树插件。我生成了两个jar和一个包含所有jar的目录。我比较了结果,当然maven-shade-plugin是最好的。我的挑战是,我有多个需要合并的spring资源,以及jax-rs和JDBC服务。与maven-assembly-plugin -plugin相比,shade插件对它们进行了适当的合并。在这种情况下,spring将失败,除非您将它们复制到您自己的resources文件夹并一次手工合并它们。两个插件都输出正确的依赖树。我有多个范围,如测试、提供、编译等,测试和提供被两个插件跳过。他们都生成了相同的清单,但是我可以使用他们的transformer将许可证与shade插件合并。使用maven-dependency-plugin当然,您不会遇到这些问题,因为jar没有被提取。但是就像有些人指出的那样,你需要多带一个文件才能正常工作。这是润色。xml的一个片段

            <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-dependency-plugin</artifactId>
            <executions>
                <execution>
                    <id>copy-dependencies</id>
                    <phase>prepare-package</phase>
                    <goals>
                        <goal>copy-dependencies</goal>
                    </goals>
                    <configuration>
                        <outputDirectory>${project.build.directory}/lib</outputDirectory>
                        <includeScope>compile</includeScope>
                        <excludeTransitive>true</excludeTransitive>
                        <overWriteReleases>false</overWriteReleases>
                        <overWriteSnapshots>false</overWriteSnapshots>
                        <overWriteIfNewer>true</overWriteIfNewer>
                    </configuration>
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-assembly-plugin</artifactId>
            <version>2.6</version>
            <configuration>
                <archive>
                    <manifest>
                        <addClasspath>true</addClasspath>
                        <mainClass>com.rbccm.itf.cdd.poller.landingzone.LandingZonePoller</mainClass>
                    </manifest>
                </archive>
                <descriptorRefs>
                    <descriptorRef>jar-with-dependencies</descriptorRef>
                </descriptorRefs>
            </configuration>
            <executions>
                <execution>
                    <id>make-my-jar-with-dependencies</id>
                    <phase>package</phase>
                    <goals>
                        <goal>single</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-shade-plugin</artifactId>
            <version>2.4.3</version>
            <configuration>
                <shadedArtifactAttached>false</shadedArtifactAttached>
                <keepDependenciesWithProvidedScope>false</keepDependenciesWithProvidedScope>
                <transformers>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                        <resource>META-INF/services/javax.ws.rs.ext.Providers</resource>
                    </transformer>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                        <resource>META-INF/spring.factories</resource>
                    </transformer>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                        <resource>META-INF/spring.handlers</resource>
                    </transformer>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                        <resource>META-INF/spring.schemas</resource>
                    </transformer>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
                        <resource>META-INF/spring.tooling</resource>
                    </transformer>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer"/>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer"/>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.ApacheLicenseResourceTransformer">
                    </transformer>
                </transformers>
            </configuration>
            <executions>
                <execution>
                    <goals>
                        <goal>shade</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>

#28


1  

Add to pom.xml:

添加pom.xml:

  <dependency>
            <groupId>com.jolira</groupId>
            <artifactId>onejar-maven-plugin</artifactId>
            <version>1.4.4</version>
        </dependency>

and

<plugin>
                <groupId>com.jolira</groupId>
                <artifactId>onejar-maven-plugin</artifactId>
                <version>1.4.4</version>
                <executions>
                    <execution>
                        <goals>
                            <goal>one-jar</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>

Thats it. Next mvn package will also create one fat jar additionally, including all dependency jars.

这是它。下一个mvn包还将另外创建一个fat jar,包括所有依赖jar。

#29


0  

This blog post shows another approach with combining the maven-jar and maven-assembly plugins. With the assembly configuration xml from the blog post it can also be controlled if dependencies will be expanded or just be collected in a folder and referenced by a classpath entry in the manifest:

这篇博文展示了另一种结合maven-jar和maven-assembly插件的方法。通过博客文章中的汇编配置xml,还可以控制依赖项是否将被扩展,或者只是在文件夹中收集,并由清单中的类路径条目引用:

The ideal solution is to include the jars in a lib folder and the manifest.mf file of the main jar include all the jars in classpath.

理想的解决方案是将jar包含在lib文件夹和manifest中。主jar的mf文件包括类路径中的所有jar。

And exactly that one is described here: https://caffebig.wordpress.com/2013/04/05/executable-jar-file-with-dependent-jars-using-maven/

这里描述的就是这个:https://咖啡因big.wordpress.com/2013/04/05/executable-jar-file with-dependent-jars-using-maven/

#30


0  

Okay, so this is my solution. I know it's not using the pom.xml file. But I had the problem my programmme compiling and running on Netbeans but it failing when I tried Java -jar MyJarFile.jar. Now, I don't fully understand Maven and I think this why was having trouble getting Netbeans 8.0.2 to include my jar file in a library to put them into a jar file. I was thinking about how I used to use jar files with no Maven in Eclipse.

这就是我的解。我知道它不用pom。xml文件。但是我在Netbeans上编译和运行程序时遇到了问题,但是当我尝试Java -jar MyJarFile.jar时失败了。现在,我还没有完全理解Maven,我认为这就是为什么Netbeans 8.0.2无法将我的jar文件包含到库中,并将其放入jar文件中。我正在考虑如何使用Eclipse中没有Maven的jar文件。

It's Maven that can compile all the dependanices and plugins. Not Netbeans. (If you can get Netbeans and be able to use java .jar to do this please tell me how (^.^)v )

Maven可以编译所有依赖项和插件。不是Netbeans。(如果你能得到Netbeans和能够使用java . jar这样做请告诉我(^。^)v)

[Solved - for Linux] by opening a terminal.

[解决- Linux]通过打开终端。

Then

然后

cd /MyRootDirectoryForMyProject

Next

下一个

mvn org.apache.maven.plugins:maven-compiler-plugin:compile

Next

下一个

mvn install

This will create jar file in the target directory.

这将在目标目录中创建jar文件。

MyJarFile-1.0-jar-with-dependencies.jar

Now

现在

cd target

(You may need to run: chmod +x MyJarFile-1.0-jar-with-dependencies.jar)

(您可能需要运行:chmod +x myjarfile -1.0 jar-with- dependent .jar)

And finally

最后

java -jar MyJarFile-1.0-jar-with-dependencies.jar

Please see

请参阅

https://cwiki.apache.org/confluence/display/MAVEN/LifecyclePhaseNotFoundException

https://cwiki.apache.org/confluence/display/MAVEN/LifecyclePhaseNotFoundException

I'll post this solution in on a couple of other pages with a similar problem. Hopefully I can save somebody from a week of frustration.

我将把这个解决方案发布在其他几个有类似问题的页面上。希望我能把某人从一周的沮丧中拯救出来。