通过HTTP验证用户(而不是HTTPS)

lon*_*oat 5 security cryptography public-key-encryption

初步注意:这仅适用于个人修补工程; 我不是在这里写企业安全,如果我是,我知道比尝试编写我自己的方案更好.:-D

编辑:为了强调上述观点,我试图在"iKnowThisWouldBeABadIdeaInRealLife"下标记这个,但是因为它是> 25个字符所以不会接受它.请注意,我知道它不是商业级的!

我需要一种通过HTTP验证用户的方法(在这种情况下不能使用HTTPS).我需要知道另一端的人真的是他们所说的人(对某种程度上相当高的信心).一旦我确定用户是合法的,我不在乎客户端和服务器之间的内容是否以明文形式发送.

我正在考虑的问题是尝试从客户端向服务器发送密码而不将其作为纯文本发送.我曾考虑在javascript中尝试一些公钥加密,因为一些谷歌搜索已经发现了一些看起来很有趣的库.

这是我正在考虑的方案:

(假设AA'分别代表私钥和公钥;还有,enc(文本,密钥)dec(密文,密钥)代表加密/解密功能)

    +------------------------+------------------------------+
    |         SERVER         |            CLIENT            |
    +------------------------+------------------------------+
(1) | t = randomToken()      |                              |
(2) | enc(t, A)           -------->  c                      |
(3) |                        |       A' = getKeyFromUser()  |
(4) | p                 <--------    p=dec(c, A')           |
(5) | if (t==p)              |                              |
    |     allowAccess()      |                              |
    | else                   |                              |
    |     denyAccess()       |                              |
    +------------------------+------------------------------+
Run Code Online (Sandbox Code Playgroud)

我在这里看到的一个弱点是,正在听交换的坏兄弟,虽然他没有A,现在有一个已知的密文/明文组合,我记得从加密类是一个不好的想法.我认为一些腌制可能会以某种方式缓解这种情况?

所以这是我的[两个]问题:

  1. 这是一个"好"的计划吗?(请记住,如果此初始交换后的任何内容都是纯文本,我不会关注 - 我只是在这里尝试验证初始身份)
  2. 绕过上面提到的"已知明文/密文对"弱点的最佳方法是什么?盐?

谢谢!


编辑: 感谢所有的讨论!只是为了澄清:

  • 我并不担心向客户保证SERVER是他们所说的人.只有相反(确保客户端的服务器是他们所说的)
  • 我知道MITM攻击.该计划并非旨在防范它们.
  • 我知道已有很多解决方案.这对我来说纯粹是一次学习练习!我不是要重新发明轮子或建立一个更好的捕鼠器.这只是为了好玩!
  • 这是我对该计划的思考过程:(我知道我并没有正确地使用公钥与私钥,但是请耐心等待一段时间)

    • 鲍勃走向爱丽丝说:"嘿,我是鲍勃."

    • 爱丽丝说,"好的.我知道鲍勃的'私钥'.如果你真的是鲍勃,请把这个秘密消息我加密(用鲍勃的私钥),并为我解密."

    • 鲍勃回复正确的消息,爱丽丝很高兴.

Ail*_*lyn 1

您基本上想在 HTTP 上实现 SSL;这在某种程度上是可行的,但永远不会像真实的那样好。

能够来回发送加密数据只是问题的一半。问题的另一部分是确保您实际上正在与服务器通信(想想中间人攻击)。

我不太确定 SSL 是如何工作的,但这是可行的方法。你应该仔细阅读一下。然而从你的计划来看,这似乎完全没有意义。为什么要将明文发送回服务器?这违背了设置此设置的目的。

我将这样做:

  1. 服务器向客户端发送随机令牌。服务器将令牌存储在“待处理”列表中。这些可以在一定的时间间隔内清除(例如:每 15 分钟)
  2. 客户端发送enc(comb(username, password, token), pubKey)回服务器,其中comb()有一些组合用户名、密码和随机令牌的函数。
  3. decomb(dec(message, privKey))服务器使用wheredecomb()的倒数取回用户名和密码comb()
  4. 服务器检查令牌是否存在于待处理列表中。如果不是,请拒绝登录尝试。如果是,则服务器可以照常继续执行身份验证。

如果生成的令牌从不重复,攻击者就不能重新发送相同的加密消息,也不能解密该消息以找出所有内容。