在 jar 文件中设置 java.library.path

Set java.library.path inside a jar file

我正在尝试为项目创建一个可执行 jar 文件,该项目在项目本身 中有一个 java 库资源文件夹作为依赖项 。我想部署那个 jar,而不需要用户单独下载那个依赖项。所以我将 java 库作为资源添加到我的项目中并构建了它。在项目源代码中,我有以下代码来尝试设置 "java.library.path" 以包含该资源。

我的代码如下所示:

URL url = Staple.class.getResource("/path/to/java_library_name");
String stringUrl = url.toString();
System.setProperty( "java.library.path", stringUrl );  
Field fieldSysPath = ClassLoader.class.getDeclaredField( "sys_paths" );  
fieldSysPath.setAccessible( true );  
fieldSysPath.set( null, null ); 

但是,当构建代码并尝试执行 jar 本身时,这不起作用,我收到以下错误:

no java_library_name in java.library.path: [jar, file, /path/to/project/target/jar_name-0.0.1-SNAPSHOT-jar-with-dependencies.jar!/path/to/java_library_name]
at java.base/java.lang.ClassLoader.loadLibrary(ClassLoader.java:2660)
at java.base/java.lang.Runtime.loadLibrary0(Runtime.java:829)
at java.base/java.lang.System.loadLibrary(System.java:1867)
.....

以上代码有什么问题?看起来它把整个路径弄错了,组成了类似 /path/to/project/target/jar_name-0.0.1-SNAPSHOT-jar-with-dependencies.jar!/path/to/java_library_name
的东西 在创建 jar 之后以及在运行时期间,我如何以编程方式检索包含 java 库文件夹的路径?

原生资源(你试图用loadLibrary加载的资源)需要是FILESMyClass.class.getResource返回的资源是URL;故意的,因为它们不需要是文件。事实上,它们通常不是,就像这里的情况一样:您的资源不是文件。它是 jar 文件中的 zip 条目,它不是文件。

没有办法解决这个问题; OS限制。

我知道,我知道。糟透了。但是你必须这样做:将 DLL 解压到一个临时位置(你可以这样做;使用 getResourceAsStream 代替,并使用新的 Files API 将它复制到一个文件;它是一个-liner 这些天 (Files.write),然后加载它。

当然,将可执行代码写入临时目录然后执行是非常安全敏感的;对于这个困境,我没有解决方案。