REST API授权和认证(Web + 移动)

75

我了解过OAuth、Amazon REST API、HTTP Basic/Digest等,但无法将它们整合到“单一组件”中。以下链接可能是最接近的情况 - 为移动应用程序创建API - 认证和授权

我想构建以API为中心的网站服务。因此(起初),我会有一个API在中心位置,网站(PHP + MySQL)通过cURLAndroidiPhone通过它们的网络接口连接。因此,有3个主要客户端 - 3个API密钥。任何其他开发人员也可以通过API接口进行开发,并获得自己的API密钥。基于用户级别状态,如果我是管理员,可以删除任何内容等,所有其他人只能操作其本地(帐户)数据,API操作将被接受/拒绝。

首先,关于授权 - 我应该使用oAuth + xAuth还是我的某种自己的实现(参见http://docs.amazonwebservices.com/AmazonCloudFront/latest/DeveloperGuide/RESTAuthentication.html?r=9197)?据我所知,在Amazon服务中,用户等同于API用户(拥有API密钥)。在我的服务中,我需要区分标准用户/帐户(在网站上注册的用户)和开发人员帐户(应该拥有自己的API密钥)。

因此,我首先需要授权API密钥,然后验证用户本身。如果我使用Amazon的方案来检查开发人员的API密钥(授权其应用程序),那么我应该使用什么方案来进行用户身份验证?

我阅读了有关通过api.example.org/auth获取令牌的内容,该令牌是在使用HTTPS和HTTP基本身份验证后发送我的用户名和密码,然后在每个后续请求中进行转发。如果我同时在Android网站上登录,该如何管理令牌?如果我仅在第一个请求(传输用户名和密码时)使用SSL,而在每个其他请求上仅使用HTTP,那么中间人攻击会怎样?在这个例子中(密码保护REST服务),这不是一个问题吗?

1个回答

133

一如既往,保护密钥的最佳方式是不传输它。

话虽如此,我们通常使用一种方案,每个“API密钥”都有两个部分:一个非秘密ID(例如1234)和一个秘密密钥(例如byte [64])。

  • 如果您分发API密钥,请在您的服务数据库中存储它(经过盐处理和哈希处理)。
  • 如果您提供用户帐户(受密码保护),请将密码(经过盐处理和哈希处理)存储在您的服务数据库中。

现在,当消费者首次访问您的API以连接时,请让他

  • 发送“用户名”参数(“john.doe”不是机密信息)
  • 发送“APIkeyID”参数(“1234”不是机密信息)

并向他返回

  • 来自您的数据库的盐(在参数错误的情况下,只需返回一些可重复的盐 - 例如 sha1(username +“notverysecret”)。
  • 服务器的时间戳

消费者应该在会话期间存储盐,以保持事物的快速和顺畅,并且应该计算和保持客户端和服务器之间的时间偏移量。

现在,消费者应该计算API密钥和密码的盐哈希值。这样,消费者便拥有了与存储在您的数据库中相同的密码和API密钥哈希,但没有任何机密信息通过网络传输。

现在,当消费者随后访问您的API以执行实际工作时,请让他

  • 发送“用户名”参数(“john.doe”不是机密信息)
  • 发送“APIkeyID”参数(“1234”不是机密信息)
  • 发送“RequestSalt”参数(byte [64],随机,不是机密信息)
  • 发送“RequestTimestamp”参数(从客户端时间和已知偏移量中计算而得)
  • 发送“RequestToken”参数(hash(passwordhash + request_salt + request_timestamp + apikeyhash))
服务器不应接受比当前时间早超过2秒的时间戳,以使其免受重放攻击的影响。
现在,服务器可以计算与客户端相同的哈希值(passwordhash+request_salt+request_timestamp+apikeyhash),并确保:
- 客户端知道API密钥, - 客户端知道正确的密码。

1
非常好的答案,谢谢。但是我能否通过将客户端和服务器都设置为UTC时间来避免“时间偏移”?或者提供像亚马逊一样的/date GET请求来计算偏移量? - svenkapudija
1
当然可以。时间戳对于重放攻击非常重要,所以任何适合您的方法都可以。如果两端都有NTP,则可以省略偏移量计算步骤。 - Eugen Rieck
1
你使用哪种哈希方法来确保盐的长度足够?有人说要尽可能安全-使用SHA256/512,甚至使用HMAC? - svenkapudija
1
我们使用带有约100字节盐的sha256。这应该需要天文资源才能还原。 - Eugen Rieck
8
TLS/SSL有很多值得称赞的地方,其中一个重要部分是它可以提供整个对话的保密性。然而,也有很多缺点:配置可能很麻烦,特别是在使用异型设备或操作系统时。如果您只需要验证身份而不需要保密性,那么上述解决方案是最好的选择。 - Eugen Rieck
显示剩余27条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接