RESTful身份验证意味着什么?它是如何工作的?我在谷歌上找不到好的概览。我唯一的理解是在URL中传递会话密钥(记住),但这可能是错误的。


当前回答

老实说,我在这里看到了很好的答案,但让我有点困扰的是,当有人将整个无状态概念推向极端,使其变得教条化时。这让我想起了那些只想拥抱纯OO的Smalltalk老粉丝,如果某个东西不是对象,那么你就错了。放过我

RESTful方法应该让你的生活更轻松,减少会议的开销和成本,尽量遵循它,因为这是一件明智的事情,但一旦你遵循一个纪律(任何纪律/准则)到了极致,它不再提供其预期的好处,那么你就错了。当今一些最好的语言同时具备函数式编程和面向对象。

如果解决问题的最简单方法是将身份验证密钥存储在cookie中并通过HTTP标头发送,那么就这样做吧,不要滥用它。请记住,当会话变得沉重和庞大时,会话是不好的,如果所有会话都由一个包含密钥的短字符串组成,那么有什么大不了的?

我愿意接受评论中的更正,但我只是认为(到目前为止)避免在我们的服务器中保存一本大字典的哈希值,这没有什么意义。

其他回答

如何在RESTful客户机-服务器架构中处理身份验证是一个有争议的问题。

通常,在SOA over HTTP世界中,可以通过以下方式实现:

HTTPS上的HTTP基本身份验证;Cookie和会话管理;HTTP报头中的令牌(例如OAuth 2.0+JWT);使用其他签名参数查询身份验证。

您将不得不调整,甚至更好地混合这些技术,以最好地匹配您的软件架构。

每个身份验证方案都有自己的PRO和CON,这取决于您的安全策略和软件架构的目的。

HTTPS上的HTTP基本身份验证

大多数web服务都使用基于标准HTTPS协议的第一个解决方案。

GET /spec.html HTTP/1.1
Host: www.example.org
Authorization: Basic QWxhZGRpbjpvcGVuIHNlc2FtZQ==

它很容易实现,默认情况下在所有浏览器上都可以使用,但也有一些已知的缺点,比如浏览器上显示的糟糕的身份验证窗口,它将持续存在(这里没有类似LogOut的功能)、服务器端的额外CPU消耗、,以及用户名和密码(通过HTTPS)传输到服务器的事实(在键盘输入期间,只让密码留在客户端,并作为安全散列存储在服务器上,应该更安全)。

我们可以使用摘要式身份验证,但它也需要HTTPS,因为它容易受到MiM或Replay攻击,并且是HTTP特有的。

通过Cookie进行会话

老实说,在服务器上管理的会话并不是真正无状态的。

一种可能是维护cookie内容中的所有数据。而且,根据设计,cookie是在服务器端处理的(事实上,客户端甚至不尝试解释cookie数据:它只是在每次连续请求时将其返回给服务器)。但是这个cookie数据是应用程序状态数据,所以客户端应该在一个纯无状态的世界中管理它,而不是服务器。

GET /spec.html HTTP/1.1
Host: www.example.org
Cookie: theme=light; sessionToken=abc123

cookie技术本身是HTTP链接的,因此它不是真正的RESTful,应该是独立于协议的,IMHO。它容易受到MiM或Replay攻击。

通过令牌(OAuth2)授予

另一种方法是在HTTP标头中放置令牌,以便对请求进行身份验证。例如,OAuth 2.0就是这样做的。请参阅RFC 6749:

 GET /resource/1 HTTP/1.1
 Host: example.com
 Authorization: Bearer mF_9.B5f-4.1JqM

简而言之,这与cookie非常相似,并存在相同的问题:不是无状态的,依赖于HTTP传输细节,并且存在许多安全漏洞,包括MiM和Replay,因此只能通过HTTPS使用。通常,JWT用作令牌。

查询身份验证

查询身份验证包括通过URI上的一些附加参数对每个RESTful请求进行签名。请参阅本参考文章。

在本文中定义如下:

所有REST查询都必须通过签名查询参数进行身份验证按小写字母顺序使用专用凭据排序作为签名令牌。签名应在URL编码查询字符串。

这种技术可能与无状态体系结构更为兼容,也可以通过轻会话管理(使用内存会话而不是DB持久性)来实现。

例如,这里有一个来自上面链接的通用URI示例:

GET /object?apiKey=Qwerty2010

应按如下方式发送:

GET /object?timestamp=1261496500&apiKey=Qwerty2010&signature=abcdef0123456789

要签名的字符串是/object?apikey=Qwerty2010&timestamp=1261496500,签名是使用API密钥的私有组件的该字符串的SHA256哈希。

服务器端数据缓存始终可用。例如,在我们的框架中,我们在SQL级别而不是URI级别缓存响应。因此,添加此额外参数不会破坏缓存机制。

有关基于JSON和REST的客户机服务器ORM/SOA/MVC框架中RESTful身份验证的一些详细信息,请参阅本文。由于我们不仅允许通过HTTP/1.1进行通信,而且还允许通过命名管道或GDI消息(本地)进行通信,因此我们尝试实现真正的RESTful身份认证模式,而不依赖HTTP特定性(如标头或cookie)。

稍后注意:在URI中添加签名可能被视为不好的做法(例如,因为它会出现在http服务器日志中),因此必须进行缓解,例如通过适当的TTL来避免重播。但如果你的http日志被破坏,你肯定会有更大的安全问题。

在实践中,即将推出的OAuth 2.0 MAC令牌认证可能是对“令牌授权”当前方案的巨大改进。但这仍然是一项正在进行的工作,与HTTP传输有关。

结论

值得总结的是,REST不仅是基于HTTP的,即使在实践中,它也主要通过HTTP实现。REST可以使用其他通信层。因此,RESTful身份验证不仅仅是HTTP身份验证的同义词,无论谷歌如何回答。它甚至根本不应该使用HTTP机制,而是应该从通信层抽象出来。如果您使用HTTP通信,由于Let's Encrypt倡议,没有理由不使用适当的HTTPS,这是除了任何身份验证方案之外所必需的。

这就是实现这一点的方法:使用OAuth 2.0进行登录。

您可以使用Google以外的其他身份验证方法,只要它支持OAuth。

使用公钥基础结构(其中密钥的注册涉及适当的绑定)可确保公钥以确保不可抵赖的方式绑定到分配给其的个人

看见http://en.wikipedia.org/wiki/Public_key_infrastructure . 如果您遵循正确的PKI标准,可以识别并锁定不正确使用被盗密钥的人或代理。如果要求代理使用证书,则绑定变得非常紧密。一个聪明且行动迅速的小偷可以逃跑,但他们会留下更多的面包屑。

首先也是最重要的,RESTful web服务是无状态的(或者换句话说,无会话的)。因此,RESTful服务没有也不应该包含会话或cookie的概念。在RESTful服务中进行身份验证或授权的方法是使用RFC 2616 HTTP规范中定义的HTTP授权头。每个请求都应该包含HTTP授权头,并且请求应该通过HTTPs(SSL)连接发送。这是在HTTPRESTful web服务中进行身份验证和验证请求授权的正确方法。我已经为Cisco Systems的Cisco PRIME Performance Manager应用程序实现了RESTful web服务。作为web服务的一部分,我还实现了身份验证/授权。

我认为restful身份验证涉及将身份验证令牌作为请求中的参数传递。示例是api对apikey的使用。我认为使用cookie或http身份验证不合格。