为了账号安全,请及时绑定邮箱和手机立即绑定

以编程方式检测 JRE 中的预览模式

以编程方式检测 JRE 中的预览模式

慕田峪7331174 2023-10-13 10:20:03
从 Java 11 开始,可以启用 Java 编译器和运行时的预览模式。它允许预览新功能。(日本EP 12)java --enable-preview如何从 Java 内部检测JVM 是否已在启用预览模式的情况下启动?目的是在应用程序内状态页面/json 上描述正在运行的容器 - 用于 DevOps 概述。到目前为止,我研究了系统属性和标志,但都没有包含任何提示。
查看完整描述

1 回答

?
守着星空守着你

TA贡献1799条经验 获得超8个赞

您可以检查Java类文件minor_version。如果0xFFFF类文件是用--enable-preview编译的。

下面给出了一个用于检查这一点的简单程序(注意,启用了预览功能的 Java 13 代码!)。

public final class ClassFileVersion {


    private final int major;

    private final int minor;


    private ClassFileVersion(int major, int minor) {

        this.major = major;

        this.minor = minor;

    }


    public static ClassFileVersion of(Class<?> classFile) throws IOException {

        try (InputStream is = classFile.getResourceAsStream("/%s.class".formatted(classFile.getName().replace('.', '/')))) {

            var buffer = new byte[8];

            if (is.read(buffer) != buffer.length) {

                throw new AssertionError("Not a Java Class File!");

            }

            return new ClassFileVersion(readUnsignedShort(buffer, 6), readUnsignedShort(buffer, 4));

        }

    }


    public String getVersionNumber() {

        return "%d.%d".formatted(major, minor);

    }


    public boolean isEnablePreview() {

        return major >= 55 && minor == 0xFFFF;

    }


    @Override

    public String toString() {

        return (major < 49 ? "JDK " : "Java SE ") +

            switch(major) {

                case 45 -> "1.1";

                case 46 -> "1.2";

                case 47 -> "1.3";

                case 48 -> "1.4";

                case 49 -> "5";

                case 50 -> "6";

                case 51 -> "7";

                case 52 -> "8";

                case 53 -> "9";

                case 54 -> "10";

                case 55 -> "11";

                case 56 -> "12";

                case 57 -> "13";

                case 58 -> "14";

                default -> throw wrongVersion();

            } +

            switch(minor) {

                case 0 -> "";

                case 3 -> {

                    if (major != 45) {

                        throw wrongVersion();

                    }

                    yield "";

                }

                case 0xFFFF -> " --enable-preview";

                default -> throw wrongVersion();

            };

    }


    private static int readUnsignedShort(byte[] buffer, int offset) {

        return ((buffer[offset] & 0xff) << 8) + (buffer[++offset] & 0xff);

    }


    private AssertionError wrongVersion() {

        return new AssertionError("Wrong Java Class File Version: %d.%d".formatted(major, minor));

    }

    // to run this code (JDK 13 needed):

    // java --enable-preview --source 13 ClassFileVersion.java 

    public static void main(String[] args) throws IOException {

        // prints "Java SE 13 --enable-preview"

        System.out.println(ClassFileVersion.of(ClassFileVersion.class));

    }


}


查看完整回答
反对 回复 2023-10-13
  • 1 回答
  • 0 关注
  • 75 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信