RESTful API 的 URI 结构

9

我使用基本身份验证,所以URI看起来像这样:http://test:password@site.com/

如果我想给所有用户,我创建一个类似http://test:password@site.com/users/的URI

但是如果我想给特定的用户,我应该使用什么地址?

http://test:password@site.com/users/test/ 

或者只是
http://test:password@site.com/test/

或者我不知道。
我提出这个问题的原因是,这种授权类型意味着URI已经包含了用户名。
提前感谢。

2
你所描述的并不是基本身份验证。基本身份验证(我指的是HTTP基本身份验证)使用授权头来传递编码的用户名/密码,并完全避免将其放在URL中。为什么要发明这个方案呢? - Jonathan W
3个回答

6
以分层的方式创建资源URI有一个好处,就是您不会遇到任何ID冲突的问题。如果您添加另一种资源类型(例如“角色”)并具有ID“test”,则您的替代版本http://test:password@site.com/test/可能会出现问题。您必须确保您的ID在所有资源类型上都是唯一的,而不仅仅是针对特定类型。此外,您的资源URI指向用户还是角色已经不再清晰。
虽然REST不一定需要,但对于我们人类来说,这是使REST API更易于理解的命名之一:“用户资源可以在包含“users”标签的URI中找到”。REST本身实际上是URI无关的,所以它真的不应该有所区别。但是,如果您想使用有意义(可读性强)的URI,我会建议您这样做。
GET http://test:password@site.com/users/

将返回所有用户。
POST http://test:password@site.com/users/ 

将创建一个新用户并分配新的URI新资源。

PUT http://test:password@site.com/users/test

将更改标识为此URI的用户资源,为实现合理的期望,您应该能够获取此用户资源

GET http://test:password@site.com/users/test

最后需要考虑的是:授权用户可能希望访问不同用户的用户资源(目前这种情况似乎不太可能出现)。
GET http://another:password@site.com/users/test

1
这是一个很好的问题。我查看了Fielding关于REST的章节HTTP规范Basic auth RFC,但似乎找不到明确的答案,但我的最佳猜测是URI中的身份验证部分不被视为资源标识的一部分。这意味着你应该假装它不存在并使用:
//site.com/users/test/

作为单个用户的URI。以下是我的理由。
  1. 浏览器实现 - URI的认证部分(test:password@)在我当前版本的Chrome和Firefox中自动隐藏,而Internet Explorer则根本不允许直接输入

  2. 如果user:password@部分使资源URI唯一,则每个用户的每个资源都将是唯一的。这对我来说似乎有点疯狂过度了。

  3. 您永远不会想要在外部引用中包含用户名和密码,如下所示:

<a href="https://admin:swordfish@site.com/users/">以管理员身份登录!</a>

我认为,在URL中包含身份验证信息是一种破坏无状态性并违反第一个REST接口约束(资源标识)的黑客行为,但它填补了某种需求,因此我们将其搁置,并假装它实际上不是URL的一部分。


0

你使用这种方法所面临的基本问题是URL

//user:password@site.com/test

等同于

//site.com/test

当你使用用户名和密码作为HTTP身份验证标头时

我认识的大多数开发人员不喜欢通过URL传递用户/密码,因此他们会选择第二个选项。现在你有一个有趣的问题,因为你有两个完全相同的URL指向完全相同的资源,这与REST相违背,更重要的是,它与HTTP缓存相违背。

当你的用户经过任何代理服务器(而他们无法控制,因为很多代理服务器可以和将被组织和ISP使用)时,你可能会向不同的用户提供缓存版本的用户。不好。

用户和密码实际上并不是URL的一部分。它们是大多数浏览器用于传递http基本AUTH标头的机制,但这不是URL,因此您需要为唯一的资源提供唯一的URI。这就是REST方式,在GET请求的情况下,如果不这样做,您应该担心。

顺便说一下,请务必告诉我您是否打算为此实现https。在http上传递用户和密码是一个非常糟糕的想法。即使您使用HTTPS,鼓励用户通过URI传递用户/密码意味着用户和密码将清晰可见于系统的每个日志(apache/nginx、应用服务器...)。这相当丑陋。因此,我建议您使用https,并阻止用户通过URL传递AUTH数据。AUTH数据应作为POST请求的正文部分或标头传递。

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