在 JDK 9 和 10 中,曾经有一些包含 Java EE 类的模块,例如 java.xml.bind。它们被标记为已弃用,并随着 JDK 9 的出现而被删除,并最终在 11 中被删除(请参阅 JEP 320 )。在我参与的产品中,曾经对 javac
编译器选项 --add-modules
进行测试,将这些模块添加为根模块。这些测试已在 JDK 11+ 中停用。如果有任何其他默认情况下也是非 root 的 JDK 模块,我不想删除它们,而是想重新激活它们。然后测试可以只使用这些模块。
我知道我可以用我自己的模块测试 --add-modules
,但是我必须在模块路径上指定它们。如果仍然存在需要测试的 JDK 11+ 模块,则通过 --add-modules
添加的 JDK 模块不需要额外的模块路径的测试用例也很有趣。我不是在谈论非导出的包,而是在谈论非根 JDK 模块。
那么,根据this answer中的信息,我实际上正在寻找系统模块中的非java.*
模块,这些模块不在没有限定的情况下导出至少一个包。在这种情况下,这些模块不应该是根模块,并且它们符合我的测试用例的条件。
更新:我正在寻找 JDK 9 中的等效项:
import javax.xml.bind.JAXBContext;
public class UsesJAXB {
JAXBContext context;
}
xx> "C:\Program Files\Java\jdk-9.0.4\bin"\javac UsesJAXB.java
UsesJAXB.java:1: error: package javax.xml.bind is not visible
import javax.xml.bind.JAXBContext;
^
(package javax.xml.bind is declared in module java.xml.bind, which is not in the module graph)
1 error
xx> "C:\Program Files\Java\jdk-9.0.4\bin"\javac --add-modules java.xml.bind UsesJAXB.java
看到了吗?使用 --add-modules
可以构建,没有它则不能。
我正在 JDK 11-18 中寻找模块(如果有),在简单程序中导入它们的类时会产生相同的结果,即要求通过 --add-modules< 显式添加它们
用于编译(不谈论运行时)。
最佳答案
您可以通过以下方式列出jdk的所有模块:
java --list-modules
然后您可以使用以下方式打印模块描述符:
java --describe-module a.module.name
在一个小脚本中过滤这些输出后,以下是我的 JDK 17 中符合条件的模块:
jdk.charsets
jdk.crypto.cryptoki
jdk.crypto.ec
jdk.editpad
jdk.internal.vm.compiler
jdk.internal.vm.compiler.management
jdk.jcmd
jdk.jdwp.agent
jdk.jlink
jdk.jpackage
jdk.localedata
jdk.zipfs
例如,jdk.charsets
是一个提供服务的模块。
问题更新后更新
因此,您正在寻找一个导出包但在未命名模块中编译类时不在默认模块图中的模块。根据 JEP,只有 java.*
模块才有资格。
当我直接或间接查找 java.se
(存在时为根模块)所需的模块时,我会看到所有 java.*
JDK 的模块,但是 java.smartcardio
。由于一些未知的魔力,java.smartcardio
也在默认图中:我尝试编译一个导入其类之一的类,并且它无需 --add-modules
即可工作>.
所以我认为你需要使用一个非java模块,不导出任何包(例如jdk.charsets
),导入其类之一(例如sun.nio.cs.ext .ExtendedCharsets
)以及:
- 在编译测试类时,除了
--add-modules
之外,还添加--add-exports
,以便javac
成功。< - 或者解析
javac
的错误消息并区分“不在模块图中”和“未导出”。
关于java - 是否有任何 JDK 11+ 系统模块不是根模块?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/71657385/