REST API PATCH or PUT

I want to design my rest endpoint with the appropriate method for the following scenario.

There is a group. Each group has a status. The group can be activated or inactivated by the admin.

Should i design my end point as

PUT /groups/api/v1/groups/{group id}/status/activate

OR

PATCH /groups/api/v1/groups/{group id}

with request body like 
{action:activate|deactivate}

The PATCH method is the correct choice here as you're updating an existing resource - the group ID. PUT should only be used if you're replacing a resource in it's entirety.

Further information on partial resource modification is available in RFC 5789. Specifically, the PUT method is described as follows:

Several applications extending the Hypertext Transfer Protocol (HTTP) require a feature to do partial resource modification. The existing HTTP PUT method only allows a complete replacement of a document. This proposal adds a new HTTP method, PATCH, to modify an existing HTTP resource.


The R in REST stands for resource

(Which isn't true, because it stands for Representational, but it's a good trick to remember the importance of Resources in REST).

About PUT /groups/api/v1/groups/{group id}/status/activate : you are not updating an "activate". An "activate" is not a thing, it's a verb. Verbs are never good resources. A rule of thumb: if the action, a verb, is in the URL, it probably is not RESTful .

What are you doing instead? Either you are "adding", "removing" or "updating" an activation on a Group, or if you prefer: manipulating a "status"-resource on a Group. Personally, I'd use "activations" because they are less ambiguous than the concept "status": creating a status is ambiguous, creating an activation is not.

  • POST /groups/{group id}/activation Creates (or requests the creation of) an activation.
  • PATCH /groups/{group id}/activation Updates some details of an existing activation. Since a group has only one activation, we know what activation-resource we are referring to.
  • PUT /groups/{group id}/activation Inserts-or-replaces the old activation. Since a group has only one activation, we know what activation-resource we are referring to.
  • DELETE /groups/{group id}/activation Will cancel, or remove the activation.
  • This pattern is useful when the "activation" of a Group has side-effects, such as payments being made, mails being sent and so on. Only POST and PATCH may have such side-effects. When eg a deletion of an activation needs to, say, notify users over mail, DELETE is not the right choice; in that case you probably want to create a deactivation resource: POST /groups/{group_id}/deactivation .

    It is a good idea to follow these guidelines, because this standard contract makes it very clear for your clients, and all the proxies and layers between the client and you, when it is safe to retry, and when not. Let's say the client is somewhere with flaky wifi, and its user clicks on "deactive", which triggers a DELETE : If that fails, the client can simply retry, untill it gets a 404, 200 or anything else it can handle. But if it triggers a POST to deactivation it knows not to retry: the POST implies this.
    Any client now has a contract, which, when followed, will protect against sending out 42 emails "your group has been deactivated", simply because its HTTP-library kept retrying the call to the backend.

    Updating a single attribute: use PATCH

    PATCH /groups/{group id}

    In case you wish to update an attribute. Eg the "status" could be an attribute on Groups that can be set. An attribute such as "status" is often a good candidate to limit to a whitelist of values. Examples use some undefined JSON-scheme:

    PATCH /groups/{group id} { "attributes": { "status": "active" } }
    response: 200 OK
    
    PATCH /groups/{group id} { "attributes": { "status": "deleted" } }
    response: 406 Not Acceptable
    

    Replacing the resource, without side-effects use PUT.

    PUT /groups/{group id}

    In case you wish to replace an entire Group. This does not necessarily mean that the server actually creates a new group and throws the old one out, eg the ids might remain the same. But for the clients, this is what PUT can mean: the client should assume he gets an entirely new item, based on the server's response.

    The client should, in case of a PUT request, always send the entire resource, having all the data that is needed to create a new item: usually the same data as a POST-create would require.

    PUT /groups/{group id} { "attributes": { "status": "active" } }
    response: 406 Not Acceptable
    
    PUT /groups/{group id} { "attributes": { "name": .... etc. "status": "active" } }
    response: 201 Created or 200 OK, depending on whether we made a new one.
    

    A very important requirement is that PUT is idempotent: if you require side-effects when updating a Group (or changing an activation), you should use PATCH . So, when the update results in eg sending out a mail, don't use PUT .


    I would recommend using PATCH, because your resource 'group' has many properties but in this case, you are updating only the activation field(partial modification)

    according to the RFC5789 (https://tools.ietf.org/html/rfc5789)

    The existing HTTP PUT method only allows a complete replacement of a document. This proposal adds a new HTTP method, PATCH, to modify an existing HTTP resource.

    Also, in more details,

    The difference between the PUT and PATCH requests is reflected in the way the server processes the enclosed entity to modify the resource
    identified by the Request-URI. In a PUT request, the enclosed entity is considered to be a modified version of the resource stored on the
    origin server, and the client is requesting that the stored version
    be replaced. With PATCH, however, the enclosed entity contains a set of instructions describing how a resource currently residing on the
    origin server should be modified to produce a new version. The PATCH method affects the resource identified by the Request-URI, and it
    also MAY have side effects on other resources; ie, new resources
    may be created, or existing ones modified, by the application of a
    PATCH.

    PATCH is neither safe nor idempotent as defined by [RFC2616], Section 9.1.

    Clients need to choose when to use PATCH rather than PUT. For
    example, if the patch document size is larger than the size of the
    new resource data that would be used in a PUT, then it might make
    sense to use PUT instead of PATCH. A comparison to POST is even more difficult, because POST is used in widely varying ways and can
    encompass PUT and PATCH-like operations if the server chooses. If
    the operation does not modify the resource identified by the Request- URI in a predictable way, POST should be considered instead of PATCH
    or PUT.

    The response code for PATCH is

    The 204 response code is used because the response does not carry a message body (which a response with the 200 code would have). Note that other success codes could be used as well.

    also refer thttp://restcookbook.com/HTTP%20Methods/patch/

    Caveat: An API implementing PATCH must patch atomically. It MUST not be possible that resources are half-patched when requested by a GET.

    链接地址: http://www.djcxy.com/p/7098.html

    上一篇: 使用PUT端点在REST API中创建资源时的状态码

    下一篇: REST API PATCH或PUT