返回

如何在 Wildfly 23 和 JDK 17 中解决 SRV 记录搜索问题?

java

如何在 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 版本中继续平稳运行。

常见问题解答

  1. 为什么在 JDK 17 中会隐藏 DnsContextFactory?

    这是由于模块化的更改,旨在提高安全性和性能。

  2. LdapCtxFactory 是否与 DnsContextFactory 一样好?

    LdapCtxFactory 直接连接到 LDAP 服务器,可以使用 JNDI API 搜索 SRV 记录。

  3. 我应该使用哪些第三方库进行 SRV 记录搜索?

    一些流行的选择包括 Apache Commons Net DNS 和 DNS Java 库。

  4. 为什么在迁移到 JDK 17 后会遇到这个错误?

    这是由于底层平台更改,需要调整应用程序以使用不同的类或技术。

  5. 这个解决方案是否适用于所有使用 JNDI 的应用程序?

    此解决方案主要适用于搜索 SRV 记录的应用程序。对于其他 JNDI 用例,可能需要采用不同的方法。