他们中的许多人对如何撰写安全的休息网络服务感到困惑,对于那些对使用这篇文章的方法感到困惑的人来说,这将有很大的帮助。
编写REST服务的可能方式(部分安全)
你意识到从字面上通过HTTP传递凭据会使数据在纯文本中被嗅探;在Gawker事件之后,你意识到纯文本或弱化的东西通常是个坏主意。
您意识到哈希密码并通过网络发送哈希代替纯文本密码仍然会让人们至少嗅探该帐户的用户名和密码的哈希值(令人不安)案例数量)在彩虹表中查找。
你大声说道,因为在这种情况下(实际上是一个真正的用户名/密码场景),你仍然会遇到以纯文本形式发送用户名和密码的相同问题(嗅闻流量)。
此时您即将放弃并承诺使用 OAuth ,但您坚持认为必须有一种安全但相对简单的方法来设计可以使用的公共网络API保持凭证私密。
答案 0 :(得分:4)
最佳解决方案
服务器和客户端知道公钥和私钥;只有服务器和客户端知道私钥,但每个人都可以知道公钥......谁在乎他们所知道的。 客户端创建一个唯一的HMAC(哈希),表示它对服务器的请求。它通过组合请求数据(参数和值或XML / JSON或其计划发送的任何内容)并将请求数据的blob与私钥一起散列来实现此目的。 然后,客户端将该HASH以及它将要发送的所有参数和值发送到服务器。 服务器获取请求并使用客户端使用的相同方法基于提交的值重新生成它自己的唯一HMAC(哈希)。 然后服务器比较两个HMAC,如果它们相等,则服务器信任客户端,并运行请求。
示例说明: (假设从android发送此请求,因为Android应用程序大部分是无会话的,他们不能拥有cookie或任何记住哪个用户已登录。因此,对于这种情况,当请求与其一起发送时,用户凭据也是必要的。)
这里的问题是用户名和密码可以被嗅探,因为它们是纯文本..因此,更好地在客户端加密它们并在服务器端解密它们。
现在出现了实际问题,服务器如何知道发送的请求是否是由有效客户发送的......
此解决方案是生成您的网址请求的哈希并添加 在URL的末尾哈希,然后将请求发送到 服务器。 (我们通常说的是校验和)..生成校验和 使用你自己或使用基于java的哈希生成器,如SHA1,MD5等
假设为URL请求生成了哈希值 的本地主机:8080 / REST /加密的用户名/加密密码/书籍/收藏夹强> 是一些哈希字符串adasfsjimnom123123k。所以,将其添加到您的网址
<强>本地主机:8080 / REST /加密的用户名/加密密码/书籍/收藏夹/ adasfsjimnom123123k 强>
因此,通过这种方式,您可以保护Web服务请求。只有当生成的校验和有效时,服务器才会提供所请求的详细信息。
使用Curl工具作为休息消费客户端(而不是单独的Java代码)来测试您的服务。