java - SSL 握手异常 : hostname in certificate didn't match

标签 java security ssl apache-httpclient-4.x

我正在编写一个系统,该系统必须向具有自签名证书的服务器(一个名为 ARX 的第三方程序,当前在开发期间在本地主机上运行)进行多部分发布。

我试图找到它的证书,但只能找到三个不同的jks文件; server.jksservertrust.jksserverca.jks

我尝试使用 System.setProperty("javax.net.ssl.trustStore", "Program Files\\<path>\\jksfile")每个 jks 文件。然而;当我这样做时,出现以下错误: 证书中的主机名不匹配:< localhost> != <9200416 arx sa cert>

我在 stackoverflow 上浏览了很多类似的问题,试图了解如何解决这个问题,但我无法解决我的问题。

有什么建议吗?非常感谢所有帮助。

最佳答案

证书本身似乎是可信的,因此您的 javax.net.ssl.trustStore 设置有效,但主机名不匹配。

主机名匹配是根据客户端如何识别它试图访问的主机来完成的。如果它尝试访问 https://localhost/,则证书必须对 localhost 有效。如果它试图访问 https://something-else.example,那么证书必须对 something-else.example 有效,即使 localhostsomething-else.example 是同一台机器。

证书中的标识符应位于主题备用名称扩展中,否则,应位于主题专有名称的通用名称 (CN) 中。

在这里,您的证书似乎只有一个 CN,而这个 CN 是“9200416 arx sa cert”。

原则上,您可以通过使用开发机器上的 hosts 文件将该名称指向您的本地主机来解决该问题。但是,该名称包含空格,因此它甚至不是有效的主机名。

您有几个选择:

  1. 为该应用程序重新生成证书,以便它使用正确的主机名(如果需要,调整您的 hosts 文件)。这可能只是设置时的一个错误。也许有人只是用空格填充了该名称,而没有意识到它会像证书中那样使用(例如,OpenSSL 有时称其为“您的名字”)。

  2. 将您的应用程序更改为忽略主机名验证是一个糟糕的选择。这是一个糟糕的选择,因为这会使您的代码容易受到 MITM 攻击。当然,这在 localhost 与 localhost 之间几乎无关紧要,但这是保留在代码中的那种代码。因为它会防止错误(否则会是有意的错误)发生,所以很可能会忘记从生产代码中删除它。即使在具有良好开发实践的地方,也很容易错过。这是一个糟糕的选择(只是为了强调这一点)。

    一个稍微好一点的变体是有一个自定义主机名 validator 来检查它找到的名称是否是您知道的证书中的名称。

关于java - SSL 握手异常 : hostname in certificate didn't match,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19292473/

相关文章:

java - 收到错误 10 后如何让 Google-Sign 正常工作?

php - 关于 cookie 和 javascript 的安全问题

html - 中等公共(public)站点的体面 HTTPs 实现是否始终是付费解决方案?

java - 如何签署自定义 JCE 安全提供程序

email - 尝试使用 libcurl 发送电子邮件时出现证书问题

c - 使用 openssl 的服务器程序在尝试连接 Linux 中的标准客户端时显示错误

java - 查找二维数组中 1 最多的索引和列

java - 亚马逊 MWS - getOrders

java - 为 eche RecyclerView 项目设置自定义字体

http - 我想将所有流量重定向到 http ://www. mywebsite.com