【问题标题】:Difference between java keytool commands when importing certificates or chainjava keytool命令在导入证书或链时的区别
【发布时间】:2018-01-13 07:27:39
【问题描述】:

只是想将这个问题作为“澄清”而不是解决方案提出:

java keytool 具有带有 -trustcacerts 参数的 -importcert 命令。来自官方帮助指南。

从 CA 导入证书回复

在您导入证书后,该证书对 您向其提交证书签名请求的 CA(或存在 cacerts 文件中已经有这样的证书),您可以导入 证书回复并将您的自签名证书替换为 证书链。该链是 CA 在 响应您的请求(当 CA 回复是一个链时),或者一个 构造(当 CA 回复是单个证书时)使用 已经可用的证书回复和可信证书 在您导入回复的密钥库或 cacerts 密钥库中 文件。

例如,如果您将证书签名请求发送给 VeriSign, 然后您可以使用以下内容导入回复,假设 返回的证书名为 VSMarkJ.cer:

keytool -importcert -trustcacerts -file VSMarkJ.cer

我还从keytool docs 中阅读了以下内容:

如果回复是单个 X.509 证书,keytool 会尝试 建立信任链,从证书回复开始到结束 在自签名证书(属于根 CA)。证书 回复和用于验证的证书层次结构 证书回复形成别名的新证书链。如果一个信托 链无法建立,证书回复未导入。在 在这种情况下,keytool 不会打印出证书并提示 用户来验证它,因为它很难(如果不是不可能的话) 用户来确定证书回复的真实性。

如果回复是 PKCS#7 格式的证书链,则该链是第一个 已订购(首先使用用户证书和自签名根 CA 证书最后),在 keytool 尝试匹配根 CA 之前 回复中提供的证书以及任何受信任的证书 在密钥库或“cacerts”密钥库文件中(如果 -trustcacerts 选项已指定)。如果找不到匹配项,则 打印出根 CA 证书,并提示用户 验证它,例如,通过比较显示的证书指纹 使用从其他(可信)来源获得的指纹 信息,可能是根 CA 本身。然后用户拥有 中止导入操作的选项。如果 -noprompt 选项是 但是,鉴于此,不会与用户进行交互。

如果我收到带有根 CA 和我的签名证书的证书回复,哪一个是我正确导入证书的正确命令(或者以下所有操作都将基于根 CA 的可用性):

# Assuming doesn't exist at all
keytool -import -keystore server_keystore.jks -storepass pass -alias rootCA -file ca-cert-file
keytool -import -keystore server_keystore.jks -storepass pass -alias fqdn_name -file signed_server_cert

#Assuming that root CA exists in system-wide cacerts
keytool -import -trustcacerts -keystore server_keystore.jks -storepass pass -alias fqdn_name -file signed_server_cert

对比

# Assuming that the root CA doesn't exist
keytool -importcert -keystore java_home\jre\lib\security\cacerts -storepass changeit -alias someRootCA -file root_ca_cert
keytool -importcert -trustcacerts -keystore server_keystore.jks -storepass pass -alias fqdn_name -file signed_server_cert

抱歉有任何不正确的假设,只是想通过与他人合作来理解:)

问候,

【问题讨论】:

  • 你尝试的时候发生了什么?如果您只有一个文件作为回复,#1 和 #3 怎么可能相关?他们都使用两个文件。
  • @EJP 好的,我错过了更改 - 现在更新了问题。谢谢。我的信任库 cacerts 已损坏(我认为),因为我在服务器密钥库和信任库中都使用了 -trustcacerts。只是想了解如何不弄乱顺序。我使用openssl s_client 命令检查我的服务器在打印出大量证书信息时的行为,但没有实际的数据写入/读取测试。

标签: java certificate keystore keytool ca


【解决方案1】:
# Assuming doesn't exist at all
keytool -import -keystore server_keystore.jks -storepass pass -alias rootCA -file ca-cert-file
keytool -import -keystore server_keystore.jks -storepass pass -alias fqdn_name -file signed_server_cert

这是要使用的。您需要在第一个选项上使用-trustcacerts 选项,或者对相应提示回复“是”。

#Assuming that root CA exists in system-wide cacerts
keytool -import -trustcacerts -keystore server_keystore.jks -storepass pass -alias fqdn_name -file signed_server_cert

如果您的签名证书位于cacerts 中,这将起作用。通常情况并非如此:根证书应该在那里,但可能他们使用的证书是三步或更多步深的证书。

# Assuming that the root CA is a new authority
keytool -importcert -keystore java_home\jre\lib\security\cacerts -storepass changeit -alias someRootCA -file root_ca_cert
keytool -importcert -trustcacerts -keystore server_keystore.jks -storepass pass -alias fqdn_name -file signed_server_cert

理论上看起来不错,但如果 CA 是一个新的权威机构,无论如何其他人都不会信任它,所以这是徒劳的。

请注意,当您导入签名证书时,您必须使用与生成密钥对和 CSR 时相同的密钥库文件和别名。这是一个常见的错误来源。

【讨论】:

  • 感谢您的回答 - 我试图理解您所说的“您需要 -trustcacerts 作为第一个选项或作为对提示的回复”的意思。假设不存在中间 CA 证书,-trustcacerts 不是说“通过查看系统范围的 cacerts 文件来为该证书建立信任链”吗?如果您能详细说明此声明,那就太酷了。
  • 是的。如果您不提供,keytool 会询问您是否要信任这些证书,您必须回答“是”。
  • 很棒的工作。谢谢。是的,别名会搞砸
  • 还要注意,别名实际上是什么并不重要。例如,它不需要是 FQDN。
  • 实际上,例如,如果 SSL/TLS 设置在作为分布式系统工作的服务器列表之间 - 那么最好获取基于通配符的 SAN/CN 的证书 - 你可以匹配稍后使用 FQDN。当然,这取决于如何设置服务器应用程序来进行验证i。
猜你喜欢
  • 2013-03-26
  • 2018-06-20
  • 2013-03-28
  • 2014-06-05
  • 2020-03-26
  • 2018-04-18
  • 1970-01-01
  • 2012-05-06
  • 1970-01-01
相关资源
最近更新 更多