如何在 Wildfly 23 和 JDK 17 中解决 SRV 记录搜索问题?
2024-03-08 16:41:44
如何在 Wildfly 23 和 JDK 17 中修复 SRV 记录搜索问题
引言
随着应用程序服务器不断更新,我们可能会遇到与底层平台变化相关的挑战。本文旨在解决在 Wildfly 23 和 JDK 17 中遇到的一个常见问题:在迁移过程中使用 DnsContextFactory 导致的 SRV 记录搜索异常。我们不仅将深入探讨问题的原因,还将提供可靠的解决方案,以帮助你克服这一障碍。
问题
在将 JBoss 7.4(Wildfly 23)从 JDK 11 迁移到 JDK 17 后,我们可能会遇到以下错误:
java.lang.IllegalAccessException: class org.jboss.as.naming.InitialContext cannot access class com.sun.jndi.dns.DnsContextFactory (in module jdk.naming.dns) because module jdk.naming.dns does not export com.sun.jndi.dns to unnamed module @500cd973
根本原因
此异常的根源在于 DnsContextFactory 的使用。在 JDK 11 中,该类是可用的,用于从 Java 中搜索 SRV 记录。然而,在 JDK 17 中,模块化更改导致 com.sun.jndi.dns 模块隐藏,使 DnsContextFactory 无法访问。
临时解决方案
作为一种临时解决方法,我们可以通过在启动时添加虚拟机参数来导出模块:
JAVA\_OPTS="\$JAVA\_OPTS --add-exports=jdk.naming.dns/com.sun.jndi.dns=ALL-UNNAMED"
永久解决方案
虽然临时解决方案可以解决问题,但它并不是一个长期的解决方案。相反,我们需要探索一种永久性方法。值得注意的是,我们可以使用 JNDI API 的其他功能来搜索 SRV 记录。一种替代方案是使用 LdapCtxFactory:
env.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.ldap.LdapCtxFactory");
env.put(Context.PROVIDER_URL, "ldap://_ldap._tcp.mydomain.com");
其他建议
除了永久解决方案外,我们还可以采取以下建议:
- 确保使用最新的 JNDI API。
- 考虑使用第三方库来简化 SRV 记录搜索。
- 探索使用更现代的替代方案,例如 DNS Java 库或 Apache Commons Net DNS。
结论
通过采用这些建议,你应该能够在 Wildfly 23 和 JDK 17 中成功搜索 SRV 记录,而无需依赖于 DnsContextFactory。这种永久性解决方案不仅可以解决当前的异常,还可以确保应用程序在未来的 JDK 版本中继续平稳运行。
常见问题解答
-
为什么在 JDK 17 中会隐藏 DnsContextFactory?
这是由于模块化的更改,旨在提高安全性和性能。
-
LdapCtxFactory 是否与 DnsContextFactory 一样好?
LdapCtxFactory 直接连接到 LDAP 服务器,可以使用 JNDI API 搜索 SRV 记录。
-
我应该使用哪些第三方库进行 SRV 记录搜索?
一些流行的选择包括 Apache Commons Net DNS 和 DNS Java 库。
-
为什么在迁移到 JDK 17 后会遇到这个错误?
这是由于底层平台更改,需要调整应用程序以使用不同的类或技术。
-
这个解决方案是否适用于所有使用 JNDI 的应用程序?
此解决方案主要适用于搜索 SRV 记录的应用程序。对于其他 JNDI 用例,可能需要采用不同的方法。