包括JAR在内的类路径

时间:2023-01-17 17:56:32

Is it possible to specify a Java classpath that includes a JAR file contained within another JAR file?

是否可以指定一个Java类路径,其中包含另一个JAR文件中的JAR文件?

12 个解决方案

#1


87  

If you're trying to create a single jar that contains your application and it's required libraries, there are two ways (that I know of) to do that. The first is One-Jar, which uses a special classloader to allow the nesting of jars. The second is UberJar, (or Shade), which explodes the included libraries and puts all the classes in the top-level jar.

如果您试图创建一个包含应用程序的jar,并且它是必需的库,那么有两种方法(我知道)可以做到这一点。第一个是One-Jar,它使用一个特殊的类加载器来允许嵌套jar。第二个是UberJar(或Shade),它利用包含的库并将所有类放在*jar中。

I should also mention that UberJar and Shade are plugins for Maven1 and Maven2 respectively. As mentioned below, you can also use the assembly plugin (which in reality is much more powerful, but much harder to properly configure).

我还应该提到UberJar和Shade分别是Maven1和Maven2的插件。正如下面提到的,您还可以使用assembly插件(它实际上功能强大得多,但要正确配置却困难得多)。

#2


49  

You do NOT want to use those "explode JAR contents" solutions. They definitely make it harder to see stuff (since everything is exploded at the same level). Furthermore, there could be naming conflicts (should not happen if people use proper packages, but you cannot always control this).

您不希望使用那些“爆炸JAR内容”解决方案。它们肯定会让人很难看到东西(因为所有东西都在同一水平上爆炸)。此外,可能会有命名冲突(如果人们使用适当的包,不应该发生这种冲突,但是您不能总是控制这种冲突)。

The feature that you want is one of the top 25 Sun RFEs: RFE 4648386, which Sun, in their infinite wisdom, has designated as being of low priority. We can only hope that Sun wakes up...

你想要的特性是25个太阳RFEs中的一个:RFE 4648386,太阳在他们的无限智慧中,已经被指定为低优先级。我们只能希望太阳醒来……

In the meanwhile, the best solution that I have come across (which I wish that Sun would copy in the JDK) is to use the custom class loader JarClassLoader.

同时,我遇到的最好的解决方案(我希望Sun在JDK中复制)是使用自定义类加载器JarClassLoader。

#3


27  

After some research I have found method that doesn't require maven or any 3rd party extension/program.

经过一些研究,我发现了不需要maven或任何第三方扩展/程序的方法。

You can use "Class-Path" in your manifest file.

您可以在清单文件中使用“类路径”。

For example:

例如:

Create manifest file MANIFEST.MF

创建清单文件manifest . mf

Manifest-Version: 1.0
Created-By: Bundle
Class-Path: ./custom_lib.jar
Main-Class: YourMainClass

Compile all your classes and run jar cfm Testing.jar MANIFEST.MF *.class custom_lib.jar

编译所有类并运行jar cfm测试。jar清单。曼氏金融*。类custom_lib.jar

c stands for create archive f indicates that you want to specify file v is for verbose input m means that we will pass custom manifest file

c代表create archive f,表示要指定file v代表详细输入m,表示要传递自定义manifest文件

Be sure that you included lib in jar package. You should be able to run jar in the normal way.

确保将lib包含在jar包中。您应该能够以正常的方式运行jar。

based on: http://www.ibm.com/developerworks/library/j-5things6/

基于http://www.ibm.com/developerworks/library/j-5things6/

all other information you need about the class-path do you find here

关于类路径的所有其他信息都可以在这里找到

#4


22  

Use the zipgroupfileset tag (uses same attributes as a fileset tag); it will unzip all files in the directory and add to your new archive file. More information: http://ant.apache.org/manual/Tasks/zip.html

使用zipgroupfileset标记(使用与fileset标记相同的属性);它将解压目录中的所有文件并添加到新的归档文件中。更多信息:http://ant.apache.org/manual/Tasks/zip.html。

This is a very useful way to get around the jar-in-a-jar problem -- I know because I have googled this exact * question while trying to figure out what to do. If you want to package a jar or a folder of jars into your one built jar with Ant, then forget about all this classpath or third-party plugin stuff, all you gotta do is this (in Ant):

这是解决jar-in- jar问题的一种非常有用的方法——我知道,因为我在google上搜索了这个*问题,并试图弄清楚该怎么做。如果您想将jar或jar文件打包到您的一个构建的jar中,然后忘记所有这些类路径或第三方插件程序,那么您所要做的就是(在Ant中):

<jar destfile="your.jar" basedir="java/dir">
  ...
  <zipgroupfileset dir="dir/of/jars" />
</jar>

#5


8  

If you are building with ant (I am using ant from eclipse), you can just add the extra jar files by saying to ant to add them... Not necessarily the best method if you have a project maintained by multiple people but it works for one person project and is easy.

如果您正在使用ant(我正在使用来自eclipse的ant)进行构建,您可以通过命令ant添加额外的jar文件……如果你有一个由多人维护的项目,它不一定是最好的方法,但是它适用于一个人的项目,而且很简单。

for example my target that was building the .jar file was:

例如,我构建.jar文件的目标是:

<jar destfile="${plugin.jar}" basedir="${plugin.build.dir}">
    <manifest>
        <attribute name="Author" value="ntg"/>
        ................................
        <attribute name="Plugin-Version" value="${version.entry.commit.revision}"/>
    </manifest>
</jar>

I just added one line to make it:

我只是加了一行

<jar ....">
    <zipgroupfileset dir="${external-lib-dir}" includes="*.jar"/>
    <manifest>
        ................................
    </manifest>
</jar>

where

在哪里

<property name="external-lib-dir" value="C:\...\eclipseWorkspace\Filter\external\...\lib" />

was the dir with the external jars. And that's it...

是带有外部jar的dir。就是这样……

#6


6  

Not without writing your own class loader. You can add jars to the jar's classpath, but they must be co-located, not contained in the main jar.

不编写自己的类装入器就不行。您可以向jar的类路径添加jar,但是它们必须是共同定位的,而不是包含在主jar中。

#7


2  

You need to build a custom class-loader to do this or a third-party library that supports this. Your best bet is to extract the jar from the runtime and add them to the classpath (or have them already added to the classpath).

您需要构建一个自定义类加载程序来完成此操作,或者构建一个支持此操作的第三方库。最好的方法是从运行时提取jar并将其添加到类路径中(或者已经将其添加到类路径中)。

#8


2  

I use maven for my java builds which has a plugin called the maven assembly plugin.

我在java构建中使用maven,它有一个名为maven组装插件的插件。

It does what your asking, but like some of the other suggestions describe - essentially exploding all the dependent jars and recombining them into a single jar

它按照您的要求来做,但是就像其他一些建议所描述的那样——本质上是将所有依赖的jar都爆炸并重新组合成一个jar

#9


2  

If you have eclpise IDE, you just need to export your JAR and choose "Package Required libraries into generated JAR". eclipse will automatically add the required dependant JARs into the generated JAR as well as generated some eclipse custom class loader that load these JARs automatically.

如果您有eclpise IDE,只需导出JAR并选择“将所需的库打包到生成的JAR中”。eclipse将自动将所需的依赖JAR添加到生成的JAR中,并生成一些自动加载这些JAR的eclipse自定义类加载器。

#10


1  

I was about to advise to extract all the files at the same level, then to make a jar out of the result, since the package system should keep them neatly separated. That would be the manual way, I suppose the tools indicated by Steve will do that nicely.

我打算建议在相同的级别上提取所有文件,然后根据结果生成一个jar,因为包系统应该保持它们之间的整洁隔离。那将是手工的方式,我想Steve所指的工具将会很好地做到这一点。

#11


1  

Winstone is pretty good http://blog.jayway.com/2008/11/28/executable-war-with-winstone-maven-plugin/. But not for complex sites. And that's a shame because all it takes is to include the plugin.

Winstone非常棒,http://blog.jayway.com/2008/11/28/ executablewar - Winstone -maven-plugin/。但对于复杂的网站来说则不然。这是一个遗憾,因为它所需要的只是包含插件。

#12


1  

Well, there is a very easy way if you're using Eclipse.

如果使用Eclipse,有一种非常简单的方法。

Export your project as a "Runnable" Jar file (right-click project folder from within Eclipse, select "Export..."). When you configure the export settings, be sure to select "Extract required libraries into generated Jar." Keep in mind, select "Extract..." and not "Package required libraries...".

将项目导出为“Runnable”Jar文件(在Eclipse中右键单击项目文件夹,选择“Export…”)。在配置导出设置时,请确保选择“将所需的库提取到生成的Jar中”。记住,选择“Extract…”而不是“Package required libraries…”。

Additionally: You must select a run-configuration in your export settings. So, you could always create an empty main( ) in some class and use it for your run configuration.

另外:必须在导出设置中选择run-configuration。因此,您可以在某些类中创建一个空的main(),并将其用于运行配置。

Anyway, it isn't guaranteed to work 100% of the time - as you will notice a pop-up message telling you to make sure you check the licenses of the Jar files you're including and something about not copying signature files. However, I have been doing this for years and have never encountered a problem.

无论如何,它并不能保证100%的工作—您会注意到弹出的消息,告诉您要确保检查包含的Jar文件的许可证,以及关于不复制签名文件的信息。然而,我这样做已经很多年了,从来没有遇到过问题。

#1


87  

If you're trying to create a single jar that contains your application and it's required libraries, there are two ways (that I know of) to do that. The first is One-Jar, which uses a special classloader to allow the nesting of jars. The second is UberJar, (or Shade), which explodes the included libraries and puts all the classes in the top-level jar.

如果您试图创建一个包含应用程序的jar,并且它是必需的库,那么有两种方法(我知道)可以做到这一点。第一个是One-Jar,它使用一个特殊的类加载器来允许嵌套jar。第二个是UberJar(或Shade),它利用包含的库并将所有类放在*jar中。

I should also mention that UberJar and Shade are plugins for Maven1 and Maven2 respectively. As mentioned below, you can also use the assembly plugin (which in reality is much more powerful, but much harder to properly configure).

我还应该提到UberJar和Shade分别是Maven1和Maven2的插件。正如下面提到的,您还可以使用assembly插件(它实际上功能强大得多,但要正确配置却困难得多)。

#2


49  

You do NOT want to use those "explode JAR contents" solutions. They definitely make it harder to see stuff (since everything is exploded at the same level). Furthermore, there could be naming conflicts (should not happen if people use proper packages, but you cannot always control this).

您不希望使用那些“爆炸JAR内容”解决方案。它们肯定会让人很难看到东西(因为所有东西都在同一水平上爆炸)。此外,可能会有命名冲突(如果人们使用适当的包,不应该发生这种冲突,但是您不能总是控制这种冲突)。

The feature that you want is one of the top 25 Sun RFEs: RFE 4648386, which Sun, in their infinite wisdom, has designated as being of low priority. We can only hope that Sun wakes up...

你想要的特性是25个太阳RFEs中的一个:RFE 4648386,太阳在他们的无限智慧中,已经被指定为低优先级。我们只能希望太阳醒来……

In the meanwhile, the best solution that I have come across (which I wish that Sun would copy in the JDK) is to use the custom class loader JarClassLoader.

同时,我遇到的最好的解决方案(我希望Sun在JDK中复制)是使用自定义类加载器JarClassLoader。

#3


27  

After some research I have found method that doesn't require maven or any 3rd party extension/program.

经过一些研究,我发现了不需要maven或任何第三方扩展/程序的方法。

You can use "Class-Path" in your manifest file.

您可以在清单文件中使用“类路径”。

For example:

例如:

Create manifest file MANIFEST.MF

创建清单文件manifest . mf

Manifest-Version: 1.0
Created-By: Bundle
Class-Path: ./custom_lib.jar
Main-Class: YourMainClass

Compile all your classes and run jar cfm Testing.jar MANIFEST.MF *.class custom_lib.jar

编译所有类并运行jar cfm测试。jar清单。曼氏金融*。类custom_lib.jar

c stands for create archive f indicates that you want to specify file v is for verbose input m means that we will pass custom manifest file

c代表create archive f,表示要指定file v代表详细输入m,表示要传递自定义manifest文件

Be sure that you included lib in jar package. You should be able to run jar in the normal way.

确保将lib包含在jar包中。您应该能够以正常的方式运行jar。

based on: http://www.ibm.com/developerworks/library/j-5things6/

基于http://www.ibm.com/developerworks/library/j-5things6/

all other information you need about the class-path do you find here

关于类路径的所有其他信息都可以在这里找到

#4


22  

Use the zipgroupfileset tag (uses same attributes as a fileset tag); it will unzip all files in the directory and add to your new archive file. More information: http://ant.apache.org/manual/Tasks/zip.html

使用zipgroupfileset标记(使用与fileset标记相同的属性);它将解压目录中的所有文件并添加到新的归档文件中。更多信息:http://ant.apache.org/manual/Tasks/zip.html。

This is a very useful way to get around the jar-in-a-jar problem -- I know because I have googled this exact * question while trying to figure out what to do. If you want to package a jar or a folder of jars into your one built jar with Ant, then forget about all this classpath or third-party plugin stuff, all you gotta do is this (in Ant):

这是解决jar-in- jar问题的一种非常有用的方法——我知道,因为我在google上搜索了这个*问题,并试图弄清楚该怎么做。如果您想将jar或jar文件打包到您的一个构建的jar中,然后忘记所有这些类路径或第三方插件程序,那么您所要做的就是(在Ant中):

<jar destfile="your.jar" basedir="java/dir">
  ...
  <zipgroupfileset dir="dir/of/jars" />
</jar>

#5


8  

If you are building with ant (I am using ant from eclipse), you can just add the extra jar files by saying to ant to add them... Not necessarily the best method if you have a project maintained by multiple people but it works for one person project and is easy.

如果您正在使用ant(我正在使用来自eclipse的ant)进行构建,您可以通过命令ant添加额外的jar文件……如果你有一个由多人维护的项目,它不一定是最好的方法,但是它适用于一个人的项目,而且很简单。

for example my target that was building the .jar file was:

例如,我构建.jar文件的目标是:

<jar destfile="${plugin.jar}" basedir="${plugin.build.dir}">
    <manifest>
        <attribute name="Author" value="ntg"/>
        ................................
        <attribute name="Plugin-Version" value="${version.entry.commit.revision}"/>
    </manifest>
</jar>

I just added one line to make it:

我只是加了一行

<jar ....">
    <zipgroupfileset dir="${external-lib-dir}" includes="*.jar"/>
    <manifest>
        ................................
    </manifest>
</jar>

where

在哪里

<property name="external-lib-dir" value="C:\...\eclipseWorkspace\Filter\external\...\lib" />

was the dir with the external jars. And that's it...

是带有外部jar的dir。就是这样……

#6


6  

Not without writing your own class loader. You can add jars to the jar's classpath, but they must be co-located, not contained in the main jar.

不编写自己的类装入器就不行。您可以向jar的类路径添加jar,但是它们必须是共同定位的,而不是包含在主jar中。

#7


2  

You need to build a custom class-loader to do this or a third-party library that supports this. Your best bet is to extract the jar from the runtime and add them to the classpath (or have them already added to the classpath).

您需要构建一个自定义类加载程序来完成此操作,或者构建一个支持此操作的第三方库。最好的方法是从运行时提取jar并将其添加到类路径中(或者已经将其添加到类路径中)。

#8


2  

I use maven for my java builds which has a plugin called the maven assembly plugin.

我在java构建中使用maven,它有一个名为maven组装插件的插件。

It does what your asking, but like some of the other suggestions describe - essentially exploding all the dependent jars and recombining them into a single jar

它按照您的要求来做,但是就像其他一些建议所描述的那样——本质上是将所有依赖的jar都爆炸并重新组合成一个jar

#9


2  

If you have eclpise IDE, you just need to export your JAR and choose "Package Required libraries into generated JAR". eclipse will automatically add the required dependant JARs into the generated JAR as well as generated some eclipse custom class loader that load these JARs automatically.

如果您有eclpise IDE,只需导出JAR并选择“将所需的库打包到生成的JAR中”。eclipse将自动将所需的依赖JAR添加到生成的JAR中,并生成一些自动加载这些JAR的eclipse自定义类加载器。

#10


1  

I was about to advise to extract all the files at the same level, then to make a jar out of the result, since the package system should keep them neatly separated. That would be the manual way, I suppose the tools indicated by Steve will do that nicely.

我打算建议在相同的级别上提取所有文件,然后根据结果生成一个jar,因为包系统应该保持它们之间的整洁隔离。那将是手工的方式,我想Steve所指的工具将会很好地做到这一点。

#11


1  

Winstone is pretty good http://blog.jayway.com/2008/11/28/executable-war-with-winstone-maven-plugin/. But not for complex sites. And that's a shame because all it takes is to include the plugin.

Winstone非常棒,http://blog.jayway.com/2008/11/28/ executablewar - Winstone -maven-plugin/。但对于复杂的网站来说则不然。这是一个遗憾,因为它所需要的只是包含插件。

#12


1  

Well, there is a very easy way if you're using Eclipse.

如果使用Eclipse,有一种非常简单的方法。

Export your project as a "Runnable" Jar file (right-click project folder from within Eclipse, select "Export..."). When you configure the export settings, be sure to select "Extract required libraries into generated Jar." Keep in mind, select "Extract..." and not "Package required libraries...".

将项目导出为“Runnable”Jar文件(在Eclipse中右键单击项目文件夹,选择“Export…”)。在配置导出设置时,请确保选择“将所需的库提取到生成的Jar中”。记住,选择“Extract…”而不是“Package required libraries…”。

Additionally: You must select a run-configuration in your export settings. So, you could always create an empty main( ) in some class and use it for your run configuration.

另外:必须在导出设置中选择run-configuration。因此,您可以在某些类中创建一个空的main(),并将其用于运行配置。

Anyway, it isn't guaranteed to work 100% of the time - as you will notice a pop-up message telling you to make sure you check the licenses of the Jar files you're including and something about not copying signature files. However, I have been doing this for years and have never encountered a problem.

无论如何,它并不能保证100%的工作—您会注意到弹出的消息,告诉您要确保检查包含的Jar文件的许可证,以及关于不复制签名文件的信息。然而,我这样做已经很多年了,从来没有遇到过问题。