在阅读到OpenJDK 11将得到长期支持之后,我决定创建一个小应用程序(使用Gradle)与JavaFX结合起来测试一些功能。经过一番努力,我设法创建了一个可以正常打开的Hello World .jar文件。
现在,我想进入下一步:运行.jar文件,而无需事先下载任何与Java相关的内容,因为此时安装OpenJDK只是通过正确设置PATH等来解决问题。
有关将OpenJDK 11应用程序与Java 11 JRE捆绑在一起的搜索不会返回很多答案。我觉得这很奇怪,因为据我所知,OpenJDK 11是第一个不附带JRE的产品。
所以我的问题是:如何将Java 11应用程序与运行时结合起来使用?
答案 0 :(得分:1)
您可以将整个JDK与您的应用程序捆绑在一起,并创建一个批处理脚本以使用捆绑的JDK运行您的应用程序。我知道这种方法会使您的版本大大膨胀,但是另一种方法是要求您的用户自己安装JDK,这对非技术敏锐的人来说并不简单。或者,您可以发布两个版本,一个捆绑了JDK,一个没有捆绑。
答案 1 :(得分:0)
也许您只需要稍等片刻,直到新jpackager工具的EA发行版发布即可。参见http://mail.openjdk.java.net/pipermail/core-libs-dev/2018-October/056186.html
答案 2 :(得分:0)
本地图书馆
我遇到的一个挑战是向JavaFX告知它自己的本机库(.dll
,.dylib
,.so
等)。幸运的是,加载dylib就像使用java.library.path
设置System.setProperty(...)
一样简单。
从历史上看,在Java中认为将此变量设置/认为没有意义,因为对于类加载器来说为时已晚(不及-Djava.library.path
),并且使用反射强制使用它是forbidden security violation since Java 10 ...幸运的是,JavaFX actually honors this variable naturally,没有任何违规或黑客行为,设置后即可将其领取。
// Detect the path to the currently running jar
String jarPath = new File(this.getClass().getProtectionDomain().getCodeSource().getLocation().getPath()).getCanonicalPath();
// Fix characters that get URL encoded when calling getPath()
jarPath = URLDecoder.decode(jarPath, "UTF-8");
String parentFolder = new File(jarPath).getParent();
// If libglass.dylib is next to the jar in a folder called "/bin"
System.setProperty("java.library.path", parentFolder + "/bin");
// ... then make any javafx calls
Java库
自然,.jar
文件也需要可访问。我所做的操作与通过zipping them into the distribution(制作单个大的.jar
文件)创建任何Java捆绑包一样
这些.jar
文件应与所有JavaFX 11发行版一致,并应进行捆绑。
javafx-swt.jar
javafx.base.jar
javafx.controls.jar
javafx.fxml.jar
javafx.graphics.jar
javafx.media.jar
javafx.swing.jar
javafx.web.jar
Java 8兼容性
使用上述技术的Java 8初始测试是肯定的。现在,我正在使用Java版本检测(上面的示例中未包括),并且仅针对Java 11或更高版本设置java.library.path
。 Java 8是2019年12月用于个人使用的EOL(2019年1月是商业使用的EOL),因此在客户端从一个LTS版本迁移到另一个LTS版本时,提供兼容性非常重要。
答案 3 :(得分:0)
Follow these tutorials found at the new home for JavaFX after having been spun out of Oracle to Gluon.
You will need to write code using modular Java. Add JavaFX 11 as a dependency to your project. And use the new linking/packaging tools to bundle a subset of the JDK within your app.
Learn about:
Oracle no longer intends for end-users to be installing a JRE or a JDK. Java Applets in a browser and Java Web Start app delivery are both being phased out, leaving the end-user with no need for a JRE. Java-based apps are expected to bundle their own Java implementation. The only folks consciously installing a JDK will be developers & server-side sysadmins.
Important:
Here is a flowchart diagram that may help you finding and deciding amongst the various vendors providing a Java 11 implementation.
答案 4 :(得分:0)
(使用jdk14)
首先,为了使用jlink
,您的主jar应该是一个模块。
如何??请考虑您有一个maven
项目。您只需要在module-info.java
目录中包含src/main/java
,并确保您require
您的应用程序所需的模块以及您export
包含主类的包。在大多数情况下,缺少requires
时会出现编译时错误。请记住,非模块化依赖项变成automatic modules。
您可以使用maven的copy-dependencies
来确保在target/lib
期间将所有依赖项都复制到mvn package
下。
由于jlink
的maven插件仍在alpha
中,因此您可以使用命令行。
注意:
jlink
将创建一个独立的包目录,其中包含
jlink
捆绑包一次定位一个平台。默认情况下,它是当前平台。 javafx
运行时模块也是特定于平台的。但由于它们不是jdk的一部分,我们需要始终提供包含它们的模块路径。javafx
运行时模块可以是downloaded from web,也可以通过使用相应的目标平台classifier
(win / linux / mac)来from maven repo。jlink
也可以创建跨平台捆绑包。只需将目标平台模块包括到--module-path
中即可(例如从linux:下载Windows jdk
/ javafx
,并将其jmods
目录添加到module-path
)。案例1: 构建并定位平台是相同
注意:/path-to/javafx-mods
必须提供给modulepath
,除非您使用maven(复制相关性)将所需的javafx deps复制到lib/
下。
jlink --launcher run=jdk14Example/com.example.javafx.app.Main \
--module-path ./lib:javafx-jdk14-example-1.0.0.jar:/path-to/javafx-mods \
--add-modules=jdk14Example --output app-bundle
案例2: 构建和定位平台是不同
# Building from linux for windows
jlink --launcher run=jdk14Example/com.example.javafx.app.Main \
--module-path ./lib:javafx-jdk14-example-1.0.0.jar:/path-to/jdk-win/jmods:/path-to/javafx-mods-win \
--add-modules=jdk14Example --output app-bundle
在上述两种情况下,您都获得一个包含自包含应用程序的目录,该目录可以在未安装java
/ javafx
的工作站上运行。
# if jlink targeted linux
app-bundle/bin/run
# if jlink targeted windows
app-bundle/bin/run.bat
# if jlink targeted mac
app-bundle/bin/run