我正在编写一个 RESTful api,并且正在考虑用户创建密钥的过程。我有以下几种可能:
/new/<keyname>
- 虽然这很容易,但我想我不会使用这个,因为我听说 GET 是用于检索和/或列出信息;/<keyname>
- 这对我来说似乎足够简单,但不会在请求正文中传递任何数据。我可以这样做吗?这很奇怪吗?/keys
并传入请求正文 "keyname=SomeKey"
- 这是正确的方法吗?我查看了来自 Joyent 的 这个 API ,在所有 PUT 和 POST 请求中,它们在请求正文中传递了一些数据。这是预期的吗?在 PUT 和 POST 请求中不要求请求正文真的是错误的吗?
我在 Http-WG 上问了这个问题。这是我得到的最准确的答案:
需要注意的是,没有正文的消息仍然可以携带表示,因为表示是正文(可以为零长度)和标头的组合。
参见:
http://tools.ietf.org/html/draft-ietf-httpbis-p3-payload-11#section-4
https://lists.w3.org/Archives/Public/ietf-http-wg/2010JulSep/0276.html
综上所述,POST不需要body。我希望同样的理由也适用于 PUT。
在最一般的形式中,HTTP 消息是这样的(注意可选的正文):
通用消息 = 起始行 *(消息头 CRLF) 回车换行 [消息正文] 起始行=请求行|状态行
进一步阅读可以得出:
9.5 发布 POST方法用于请求源服务器接受 请求中包含的实体作为资源的新从属 由请求行中的请求 URI 标识。 ...
和
9.6 看跌 PUT 方法请求将所包含的实体存储在 提供的请求 URI。 ... POST 和 PUT 请求之间的根本区别是 体现在Request-URI的不同含义上。中的 URI POST 请求标识将处理所附内容的资源 实体。该资源可能是一个数据接受过程,一个通往 一些其他协议,或接受注释的单独实体。 相反,PUT 请求中的 URI 标识所包含的实体 随着请求——用户代理知道 URI 的意图以及 服务器不得尝试将请求应用于其他资源。
POST 和 PUT 都包含请求中包含的短语 实体。
根据我的阅读,我相信 POST 和 PUT 都需要一个主体(我知道,这是一种非规范的描述)。
在 REST 上下文中,POST 是创建,PUT 是更新。 我可以想象创建一个空对象(也许是未来信息的占位符),但我不认为空更新有多大用途。
这不是必需的。您可以发送不带正文的 POST/PUT 请求,而是使用查询字符串参数。但要小心,如果您的参数包含 HTTP 无效的字符,您将必须对它们进行编码。
例如,如果您需要将“hello world”发布到端点,则必须使其看起来像这样:http://api.com?param=hello%20world
一句话回答你的问题。是的,正文中应该有正文/内容,但这不是必需的(强制)。
可能最好的方法是您的第三个选择:使用
/keys
发布到 keyname=SomeKey
。
原因如下:您可能希望向 API 添加另一个函数,例如
create_new_user
。 这样就很难区分尝试 POST 名为 create_new_user
的密钥的用户和尝试使用 create_new_user
功能的用户之间的区别。
您正确地说,您不应该使用 GET 来执行此操作,因为 GET 操作“不应该具有采取操作的意义” 除了检索之外。”(RFC 2616).
根据 okHttp3(Android 的 HTTP 库):以下方法需要主体:POST、PUT、PATCH、PROPPATCH (WebDAV) 和 REPORT (source)。如果您尝试使用给定方法在没有正文的情况下执行请求,它甚至会崩溃。