我一直在思考定义具有相互依赖性的资源集合的正确方法。
例如,让我们考虑可以通过URI独立访问的“文档”和“注释”:
/documents/{doc-uri}
/comments/{comment-id}
但是,我们通常希望收集与特定文档相关的评论。这就产生了一个关于如何对其进行检查的设计问题。
我可以看到几个主要选项:
1。)在文档uri之后提供一个集合uri以供评论
GET /documents/{doc-uri}/comments/
2.。)为评论集合提供一个参数,以便按文档选择
GET /comments/{comment-id}?related-doc={doc-uri}
3.使用内容协商来请求通过Accept标头返回相关的注释。
// Get all the comments for a document
GET /documents/{doc-uri} Accept: application/vnd.comments+xml
// Create a new comment
POST /documents/{doc-uri} Content-Type: application/vnd.comment+xml <comment>...</comment>
方法1的优点是可以自动将注释放在文档的上下文中。使用POST / PUT创建,更新和删除注释时,这也很好。但是,它不提供对文档上下文之外的注释的全局访问。因此,如果我们想对系统中的所有注释进行搜索,我们需要方法#2。
方法2提供了与#1相同的许多好处,但是在没有文档上下文的情况下创建注释是没有意义的。由于评论必须明确与文档相关。
方法3从GET和POST / create透视图很有意思,但是通过更新和删除会变得有点毛茸茸。
我可以看到所有这些方法的专家和骗子,所以我正在寻找一些可能已经接触并解决过这个问题的人的更多指导。
我正在考虑做两种方法1&amp; 2,因此我可以提供所需的所有功能,但我担心我可能会过度复杂/重复功能。
答案 0 :(得分:9)
REST API 必须是超媒体驱动的。请参阅超媒体作为应用程序状态引擎(HATEOAS)约束。所以,不要在URLPatterns上浪费你的时间,因为它们不是RESTful。 URLPattern暗示客户端和服务器之间的紧密耦合;简单地说,客户端必须知道URL的外观并且能够构建它们。
考虑这个REST设计用于您的用例:
文档的表示包含客户端可以POST注释或使用GET获取文档的所有注释的链接。 e.g。
{
...
"comments" : {
"href": ".. url ..",
"rel": ["create-new-comment", "list-comments"]
}
}
客户端只需获取此URL并对URL执行GET或POST方法;不知道URL是什么,看起来像。
另见这篇文章:
http://roy.gbiv.com/untangled/2008/rest-apis-must-be-hypertext-driven
答案 1 :(得分:0)
方法1和方法2的组合看起来很好,正如您在方法2中所说的那样,没有太多意义创建没有文档上下文的注释,因为两者之间存在父子关系,如果删除文档是可接受的删除他的所有评论,你可以使你的/comments/
uri成为只读资源,以避免在没有文档的情况下创建它。
正如filip26所说,rest apis应该是超媒体驱动的,但这并不意味着url模式并不重要,你可以拥有一个uri或者很多的资源,如果你的资源有多个uris,客户更容易找到它们,缺点是可能会令人困惑,因为有些客户使用一个uri而不是另一个,所以你可以使用规范的uri作为资源,当客户端通过这个规范的uri访问资源时,你可以发回200 OK
,客户请求其他人之一,你可以发回303“另见”以及规范的uri。