首页 文章

使用客户端证书代替公共Web应用程序上的密码

提问于
浏览
0

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

好像有很多问题:

  • 如何以跨浏览器方式生成密钥对? <keygen> 似乎很有用,但我需要支持Internet Explorer .

  • 如何签署密钥对并将证书输入浏览器?客户端证书的每个解释仅包括用于生成证书的openssl命令 . 我真的不想从我的Web应用程序中打开openssl .

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

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

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

以下是我认为该过程的样子:

  • 当用户注册时,他们的浏览器会生成密钥对并向服务器发送签名请求 .

  • 服务器立即返回一个已加载到浏览器中的签名证书 . 服务器将密钥指纹存储在数据库中以便稍后对用户进行身份验证 . 我不想将证书DN用作身份验证,请参阅上面有关CA妥协的信息 .

  • 前端Web服务器需要客户端证书,验证它们,并将公钥指纹发送到我的应用服务器 .

  • 应用服务器按用户的密钥指纹查找用户,现在已经过身份验证 .

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

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

1 回答

  • 2

    这有用吗?

    处理证书对于大多数用户来说都有学习曲线,包括在IT部门工作的人员 . 存储,移动和保护这些证书可能会很痛苦 . (我刚才在this question on Security.SE上写了一些关于这个主题的内容 . )

    如何以跨浏览器方式生成密钥对?看起来很有用,但我需要支持Internet Explorer . 如何签署密钥对并将证书输入浏览器?客户端证书的每个解释仅包括用于生成证书的openssl命令 . 我真的不想从我的Web应用程序中打开openssl .

    你可以在this question找到一些有用的指针 . 特别是,您可以在IE中使用ActiveX生成密钥对 . 然后,实现服务器端CA.在Java中,BouncyCastle对此非常有用,我想pyOpenSSL在Python中也很有用 .

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

    确实 .

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

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

    Apache Httpd和Java都会让你接受证书,而不会在握手过程中验证它们(或者让你自定义如何完成),分别使用 SSLVerifyClient optional_no_ca 或空 TrustManager ,但是你记得以后再进行一些验证 . 特别是,请注意不要将此应用程序与依赖于默认情况下正常PKI验证的其他应用程序混合使用处理程序,否则那些将是不安全的 .

    存在与所有这些相关的各种问题(特别是哪些证书颁发机构列表将由服务器发送,或者如何选择客户端证书) . 你会在this answer找到更多相关细节 .

相关问题