0

我有一个网络应用程序,任何人都可以在其中注册一个帐户。而不是密码,我想使用客户端证书进行身份验证。这实用吗?

好像有很多问题:

  • 如何以跨浏览器的方式生成密钥对?<keygen>看起来很有用,但我需要支持 Internet Explorer。

  • 您如何签署密钥对并将证书放入浏览器?客户端证书的每一个解释只包括用于生成证书的 openssl 命令。我真的不想从我的网络应用程序中掏出 openssl。

  • 由于服务器正在签署证书,如果它的签名 (CA) 密钥被泄露怎么办?这似乎是比密码数据库泄漏更严重的攻击,因为攻击者可以永远默默地冒充任何用户。

    我想完全避免签署证书,而只使用公钥指纹作为用户的身份。这意味着 CA 密钥的知识不能用来冒充任何人,因为他们没有用户的私钥。

  • 似乎有人应该以前做过这一切。是否有整个端到端流程的开源实现?Python 或 Django 实现会特别有帮助。

这是我认为该过程的样子:

  1. 当用户注册时,他们的浏览器会生成一个密钥对并向服务器发送一个签名请求。
  2. 服务器立即返回加载到浏览器中的签名证书。服务器将密钥指纹存储在数据库中,以便稍后对用户进行身份验证。我不想使用证书 DN 作为身份验证,请参阅上面关于 CA 妥协的信息。
  3. 前端网络服务器需要客户端证书,对其进行验证,并将公钥指纹发送到我的应用服务器。
  4. 应用服务器通过他们的密钥指纹查找用户,现在已经过身份验证。

我不想处理证书吊销。由于密钥指纹用于验证,而不是证书 DN 数据,因此仅更改与用户关联的指纹将强制使用该密钥。

编辑:我能够找到一个实现类似工作流程的演示:https ://openweb.or.kr/html5/index_en.php 。它在 IE 中不起作用,并且有我谈到的 CA 问题。

4

1 回答 1

2

这实用吗?

对于大多数用户(包括从事 IT 工作的人)来说,处理证书都有一个学习曲线。存储、移动和保护这些证书可能会很痛苦。(我不久前在 Security.SE上就这个问题写了一些关于这个主题的东西。)

如何以跨浏览器的方式生成密钥对?看起来很有用,但我需要支持 Internet Explorer。

您如何签署密钥对并将证书放入浏览器?客户端证书的每一个解释只包括用于生成证书的 openssl 命令。我真的不想从我的网络应用程序中掏出 openssl。

您可能会在这个问题中找到一些有用的指示。特别是,您可以在 IE 中使用 ActiveX 生成密钥对。然后,实现一个服务器端 CA。在 Java 中,BouncyCastle 对此非常有用,我想 pyOpenSSL 在 Python 中也很有用。

由于服务器正在签署证书,如果它的签名 (CA) 密钥被泄露怎么办?这似乎是比密码数据库泄漏更严重的攻击,因为攻击者可以永远默默地冒充任何用户。

的确。

我想完全避免签署证书,而只使用公钥指纹作为用户的身份。这意味着 CA 密钥的知识不能用来冒充任何人,因为他们没有用户的私钥。

您必须签署您的证书才能使它们成为有效的 X.509 证书,但您可以调整验证这些证书的各方以忽略签名并依赖公钥。客户端具有与证书的公钥匹配的私钥这一事实由CertificateVerifyTLS 握手中的消息保证,并且它与验证证书本身的层相当独立。

Apache Httpd 和 Java 都允许您在握手期间接受证书而不验证它们(或者让您自定义如何完成),分别使用SSLVerifyClient optional_no_ca或为空TrustManager,但您必须记住稍后执行一些验证。特别是,请注意不要将此应用程序与其他依赖于由默认处理程序完成的正常 PKI 验证的应用程序混合使用,否则这些应用程序将是不安全的。

所有这些都存在各种问题(特别是服务器要发送哪些证书颁发机构列表,或者如何选择客户端证书)。您将在此答案中找到有关此的更多详细信息。

于 2014-05-16T23:41:17.517 回答