Java 19预览特性测试代码无法运行,非测试代码正常
问题描述
在Java 19中试用Foreign Function & Memory API(预览版),通过jextract生成了netcdf_h.java文件。src目录下的main程序可正常运行,但test目录的测试程序运行时抛出如下错误:
Preview features are not enabled for sunya/cdm/netcdf/ffm/netcdf_h (class file version 63.65535). Try running with '--enable-preview'
java.lang.UnsupportedClassVersionError: Preview features are not enabled for sunya/cdm/netcdf/ffm/netcdf_h (class file version 63.65535). Try running with '--enable-preview'
当前使用的Gradle构建配置如下:
... tasks { val ENABLE_PREVIEW = "--enable-preview" withType<JavaCompile>() { options.compilerArgs.add(ENABLE_PREVIEW) // Optionally we can show which preview feature we use. options.compilerArgs.add("-Xlint:preview") // Explicitly setting compiler option --release // is needed when we wouldn't set the // sourceCompatiblity and targetCompatibility // properties of the Java plugin extension. options.release.set(19) } withType<Test>() { useJUnitPlatform() jvmArgs!!.add(ENABLE_PREVIEW) } withType<JavaExec>() { jvmArgs!!.add(ENABLE_PREVIEW) } withType<KotlinCompile> { kotlinOptions.jvmTarget = "19" } } java { toolchain { languageVersion.set(JavaLanguageVersion.of(19)) } }
解决方法
问题核心是测试代码的编译阶段未启用预览特性参数。主代码能运行是因为主编译和运行任务都配置了--enable-preview,但测试编译环节的配置存在遗漏,导致测试类无法正常引用带预览标记的netcdf_h类。
修改Gradle配置
更新tasks块,确保测试编译、运行全流程都启用预览特性:
tasks { val ENABLE_PREVIEW = "--enable-preview" // 覆盖所有Java编译任务(含主代码和测试代码) withType<JavaCompile>() { options.compilerArgs.add(ENABLE_PREVIEW) options.compilerArgs.add("-Xlint:preview") options.release.set(19) } // 测试运行阶段保持原有配置,同时确保类路径正确 withType<Test>() { useJUnitPlatform() jvmArgs!!.add(ENABLE_PREVIEW) classpath += sourceSets.main.get().output } withType<JavaExec>() { jvmArgs!!.add(ENABLE_PREVIEW) } // 若测试代码使用Kotlin,需给Kotlin编译任务也添加预览参数 withType<KotlinCompile> { kotlinOptions.jvmTarget = "19" kotlinOptions.freeCompilerArgs += ENABLE_PREVIEW } } java { toolchain { languageVersion.set(JavaLanguageVersion.of(19)) } }
IntelliJ IDE运行配置补充
如果直接用IntelliJ运行测试,还需手动在IDE配置中添加参数:
- 打开「Run/Debug Configurations」
- 找到对应的测试类或测试套件配置
- 在「VM options」栏中添加
--enable-preview - 保存后重新运行测试
核心原因
Java预览特性的类文件带有特殊版本标记(63.65535对应Java 19预览版),无论编译还是运行阶段,只要涉及这类类,必须显式启用--enable-preview。之前的配置仅覆盖了主代码编译和测试运行,漏掉了测试代码的编译环节,导致测试类加载预览类时失败。
内容的提问来源于stack exchange,提问作者John Caron

