Java JAR中包含JAR的类路径

Java JAR中包含JAR的类路径,java,classpath,Java,Classpath,可以指定包含另一个JAR文件中的JAR文件的Java类路径吗?必须编写自己的类加载器。您可以将jar添加到jar的类路径中,但它们必须位于同一位置,而不是包含在主jar中。您需要构建一个自定义类加载器来完成此操作,或者构建一个支持此操作的第三方库。最好的办法是从运行时提取jar并将其添加到类路径(或者已经将其添加到类路径)。如果您试图创建一个包含应用程序及其所需库的jar,有两种方法(我知道)可以做到这一点。第一个是,它使用一个特殊的类加载器来允许JAR嵌套。第二个是,(或),它分解包含的库,并

可以指定包含另一个JAR文件中的JAR文件的Java
类路径吗?

必须编写自己的类加载器。您可以将jar添加到jar的类路径中,但它们必须位于同一位置,而不是包含在主jar中。

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

如果您试图创建一个包含应用程序及其所需库的jar,有两种方法(我知道)可以做到这一点。第一个是,它使用一个特殊的类加载器来允许JAR嵌套。第二个是,(或),它分解包含的库,并将所有类放在顶级jar中


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

我建议在同一级别提取所有文件,然后将结果制作成jar,因为包系统应该将它们整齐地分开。
这将是手动方式,我想Steve指定的工具会很好地做到这一点。

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


它可以满足您的要求,但就像其他一些建议所描述的那样——基本上分解所有依赖的jar并将它们重新组合成一个jar

您不想使用那些“分解jar内容”的解决方案。它们肯定会让人更难看到东西(因为所有东西都是在同一水平上爆炸的)。此外,可能存在命名冲突(如果人们使用正确的软件包,则不会发生这种情况,但您无法始终控制这种情况)

你想要的特征是:,太阳以其无限的智慧将其指定为低优先级。我们只能希望太阳醒来


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

使用zipgroupfileset标记(使用与文件集相同的属性);它将解压目录中的所有文件并添加到新的存档文件中。 更多信息:

这是一个非常有用的方法来解决jar-in-a-jar问题——我知道,因为我在谷歌上搜索了这个确切的StackOverflow问题,同时试图找出该做什么。如果您想用Ant将一个jar或一个jar文件夹打包到您的一个构建的jar中,那么忘记所有这些类路径或第三方插件,您所要做的就是(在Ant中):


...

温斯顿很不错。但不适用于复杂的站点。这是一个遗憾,因为它只需要包含插件。

如果您使用ant构建(我使用的是eclipse中的ant),您只需添加额外的jar文件即可 通过告诉蚂蚁添加它们。。。 如果您有一个由多人维护的项目,那么这不一定是最好的方法,但它适用于一个人的项目,而且很简单

例如,我构建.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>

................................
我只添加了一行代码:

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

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

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

例如:

创建清单文件manifest.MF

Manifest-Version: 1.0
Created-By: Bundle
Class-Path: ./custom_lib.jar
Main-Class: YourMainClass
编译所有类并运行
jar cfm Testing.jar MANIFEST.MF*.class custom_lib.jar

c
代表创建存档
f
表示要指定文件
v
用于详细输入
m
表示我们将传递自定义清单文件

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

基于:


您可以找到关于类路径的所有其他信息。

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

将项目导出为“可运行”Jar文件(右键单击Eclipse中的项目文件夹,选择“导出…”)。配置导出设置时,请确保选择“将所需库提取到生成的Jar中”。请记住,选择“提取…”和而不是“打包所需库…”

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


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

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

提取到Uber目录对我很有用,因为我们都应该使用root:\java,并且在具有版本控制的包中包含outlets代码。Ie约-1.0.0。签名是可以的,因为jar在其下载位置完好无损。第三方签名完整,提取到c:\java。这是我的项目总监。从launcher运行,因此java-cp c:\java launcher

如果您使用的是Spring Boot,您可能需要查看以下文档:

Java不提供任何加载嵌套jar文件的标准方法 也就是说,jar文件本身包含在jar中)。这可能是 如果需要分发se,则会出现问题
<property name="external-lib-dir" 
          value="C:\...\eclipseWorkspace\Filter\external\...\lib" />
Manifest-Version: 1.0
Created-By: Bundle
Class-Path: ./custom_lib.jar
Main-Class: YourMainClass