1

我有一个基于 JavaFX 的桌面应用程序,我通过 GraalVM/GluonFX 创建本机图像。为了在运行时检索应用程序的版本,我之前 - 当应用程序只有一个胖 JAR 时 - 使用了Package#getImplementationVersion(). 但是,这会返回null

我认为这是因为我没有正确设置清单条目?我的配置gluonfx-maven-plugin

<plugin>
    <groupId>com.gluonhq</groupId>
    <artifactId>gluonfx-maven-plugin</artifactId>
    <version>1.0.10</version>
    <configuration>
        <mainClass>${mainClass}</mainClass>
        <nativeImageArgs>
            <arg>--allow-incomplete-classpath</arg>
            <arg>--initialize-at-build-time=org.pdfclown.Version</arg>
            <arg>--no-fallback</arg>
        </nativeImageArgs>
    </configuration>
</plugin>

有没有办法配置插件以Package#getImplementationVersion()返回应用程序的版本?我无法在相应的文档中找到某些内容。此外,GraalVM 中的一个相关问题已在 2020 年得到解决。

4

1 回答 1

1

假设您有一个 Maven 项目,并添加到您的主应用程序类:

@Override
public void start(Stage primaryStage) throws Exception {
    ...
    System.out.println("Main class version: " + getClass().getPackage().getImplementationVersion());
}

如果你用 shade 插件做了一个胖 jar 并注意添加所需的清单条目,比如Implementation-Version(比如说1.0),当你运行时:

java --module-path=PATH_TO_FX --add-modules javafx.controls,javafx.fxml -jar my-fat-jar.jar

它应该打印:

Main class version: 1.0

但是,如果您运行

mvn javafx:run

它打印:

Main class version: null

正如你所报告的。

原因是:类路径中没有清单,并且类(target/classes)没有打包在 jar 中。

如果您的项目具有第三方依赖项,其中包含带有Implementation-Version条目的清单(比如说2.0),请执行以下操作:

@Override
public void start(Stage primaryStage) throws Exception {
    ...
    System.out.println("3rd party Main class version: " + com.my.third.party.MainClass.class.getPackage().getImplementationVersion());
}

将工作:

mvn javafx:run
[INFO] --- javafx-maven-plugin:0.0.8:run (default-cli) @ MyProject ---
3rd party Main class version: 2.0.

因为 jar 是带有清单的打包类的依赖项。

并且做本机图像mvn gluonfx:build gluonfx:nativerun也可以:

[INFO] --- gluonfx-maven-plugin:1.0.10:nativerun (default-cli) @ MyProject ---
[Mon Dec 20 21:29:16 CET 2021][INFO] ==================== RUN TASK ====================
[Mon Dec 20 21:29:16 CET 2021][INFO] [SUB] 2021-12-20 21:29:16.810 MyProject[23068:414510] Starting Gluon VM...
[Mon Dec 20 21:29:16 CET 2021][INFO] [SUB] Dec 20, 2021 9:29:16 PM com.sun.javafx.application.PlatformImpl startup
[Mon Dec 20 21:29:16 CET 2021][INFO] [SUB] WARNING: Unsupported JavaFX configuration: classes were loaded from 'unnamed module @21c815e4'
[Mon Dec 20 21:29:16 CET 2021][INFO] [SUB] 3rd party Main class version: 2.0

所以在这一点上,我看到了三个选项:

  • 将您的核心代码移动到一个模块,发布一个 jar,并将其作为依赖项添加到您的主项目中,这应该可以工作。
  • 将清单键值移动到属性文件,并使用 Maven 资源插件。这应该使用 GluonFX 插件开箱即用(确保将属性扩展添加到资源列表)。这应该是最简单的一个。
  • 在 Substrate 上提交问题以请求清单。到目前为止,Substrate 从项目中创建了一个 jar ,所以理论上它也可以有一个清单,并且可以使用来自插件配置的一些键值来归档。添加清单很容易,问题在于将更改添加到配置以传递键值。
于 2021-12-21T17:56:47.430 回答