使用POST作为UPDATE或CREATE时是否违反RESTfulness [英] Do I violate RESTfulness when using POST as UPDATE OR CREATE

查看:64
本文介绍了使用POST作为UPDATE或CREATE时是否违反RESTfulness的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

鉴于其他部门对我们的REST API的要求,他们希望不仅将 POST 用于CREATE,而且还将其用于 UPDATE或CREATE .我知道在RESTful API中, PUT 可以或应该用于此,但是由于客户端必须更新用于构建URI的信息,因此我们不能使用它.它将更改URI,并使 PUT 不再幂等...(旧的URI在第一个 PUT 之后将不存在).
tl;博士,我们无法使用PUT

Given the requirement other departments have for our REST API they would like to use POST not just for CREATE but for UPDATE OR CREATE. I know in a RESTful API PUT could or should be used for that, but because clients have to update information that is used to build the URI, we cannot use that. It would change the URI and make PUT not idempotent anymore... (the old URI would not exist after the first PUT).
tl;dr we cannot use PUT

HTTP/1.1规范中,POST是定义为

In the HTTP/1.1 specs POST is defined as

POST方法用于请求源服务器接受请求中包含的实体作为资源的新下属由Request-URI标识

The POST method is used to request that the origin server accept the entity enclosed in the request as a new subordinate of the resource identified by the Request-URI

而且

由POST方法执行的操作可能不会导致资源可以通过URI进行识别.

The action performed by the POST method might not result in a resource that can be identified by a URI.

为了保持REST风格,我将解释更新功能为先删除旧元素,然后再创建新元素,这是 POST 可以接受的功能.

To stay RESTful I would explain the update functionality as an Deletion of the old element and then a Creation of the new one, which would be an acceptable functionality for POST I would say.

创建成功后,我们将返回#201 ,而仅是更新时,我们将返回#200 .

We would return a #201 when creation was successful and a #200 when it was just an update.

在我们的API中,有可能在没有URI的情况下寻址正确的元素(例如,用 POST 进行更新),因为所有URI构建主键部分都在资源中正文,因此API知道客户端要访问哪个元素.

In our API it is "possible" to address the right element without the URI (e.g. for updating it with POST), because all the URI building primary key parts are in the resource body, so the API knows which element the client wants to access.

(这只是 POST 行为的一个示例.不适用于资源的数据结构.当然,对于 PUT /cars/)

(This is just an example of the behavior for POST. Not for the data structure of the resource. Of course using PUT would be completely right for /cars/)

POST /cars/ HTTP/1.1
<car>
    <id>7</id>
    <status>broken</status>
</car>

响应:#201
然后

response: #201
and then

POST /cars/ HTTP/1.1
<car>
    <id>7</id>
    <status>fine</status>
</car>

响应:#200
现在/cars/7 上的 GET 将返回以下内容:

response: #200
now a GET on /cars/7 would return the following:

<car>
    <id>7</id>
    <status>fine</status>
</car>

推荐答案

违反RESTfulness"没有严格定义.

"Violating RESTfulness" is not strictly defined.

理查森成熟度模型是对接口中类似REST的行为的学位的很好的参考.a>将对REST理想的支持程度分为4层(0表示完全不是REST",3表示完全REST,但几乎没有人这样做")

A good reference to degrees of REST-like behaviour in an interface is the Richardson Maturity Model which splits degrees of support for REST ideals into 4 tiers (with 0 being "not REST at all" and 3 being "completely REST, but hardly anyone does this yet")

在此模型中的第2层基于RESTful HTTP的设计中,您的选择只会稍微中断.但是,这是许多现实世界项目必须应对的折衷方案.

Your choice breaks only slightly with RESTful HTTP-based design at level 2 within this model. However, it is the kind of compromise that many real-world projects have to contend with.

POST具有足够的开放性,可以根据需要进行幂等,但是HTTP不需要.因此,您并没有破坏HTTP,只是错过了使用更紧密的PUT方法的机会.相反的情况是,将PUT用于API的非幂等部分,会带来更多问题.

POST is open-ended enough that it can be idempotent if you wish, but HTTP does not require it to be. So you have not broken with HTTP, just missed the opportunity to use the more germane PUT method. The reverse situation, using PUT for a non-idempotent part of the API, would be more problematic.

我个人认为,如果您在处理不同的HTTP方法和路由时保持一致,并清楚地记录此更改以达到期望,则可以合理地将API称为"RESTful".我认为响应代码拆分为200/201足以编写一个自洽的客户端.尽管我希望在这里看到既创建又更新为PUT,但这并不是让我停顿片刻的原因.

As a personal opinion, I think that if you remain self-consistent when handling the different HTTP methods and routes, and document this change to expectations clearly, then you can reasonably call your API "RESTful". I think the response code split 200/201 is enough that a self-consistent client could be written. Although I would prefer to see both create and update as PUT here, it's not something that would cause me more than a moment's pause.

您可能会建议按照建议的收集路线(在示例中为 POST/cars )支持 update或create ,并在建议的路线上添加 update 物品路线( POST/cars/7 ).更新或创建"的概念在数据库和ORM框架中非常普遍,因此很容易理解.客户也可以使用后一种仅更新路由,以确保不会意外地自动创建新记录.

You might consider supporting update or create on the collection route (POST /cars in your example) as suggested, plus update on the item route (POST /cars/7). The concept of "update or create" is common enough in database and ORM frameworks, that it would be easily understood. A client could also use the latter update-only route in confidence that it would not accidentally auto-create a new record.

这篇关于使用POST作为UPDATE或CREATE时是否违反RESTfulness的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆