[Turn] RESTful API best practices

This article is reproduced from: http://www.ruanyifeng.com/blog/2018/10/restful-api-best-practices.html

 

RESTful  is currently the most popular API design specification for the design of web data interfaces.

Its general principles are easy to grasp, but the details are not easy to get right. This article summarizes the design details of RESTful and introduces how to design an API that is easy to understand and use.

1. URL design

1.1 Verb + Object

The core idea of ​​RESTful is that the data manipulation instructions issued by the client are all in the structure of "verb + object". For example, GET /articlesthis command GETis a verb and /articlesan object.

Verbs are usually five HTTP methods, corresponding to CRUD operations.

  • GET: Read
  • POST: Create
  • PUT:更新(Update)
  • PATCH: Update (Update), usually a partial update
  • DELETE: Delete

According to the HTTP specification, all verbs are capitalized.

1.2 Verb coverage

Some clients use only GETand POSTboth methods. The server must accept the POSTanalog three other methods PUT( PATCH, DELETE, ).

At this time, the HTTP request sent by the client must add X-HTTP-Method-Overrideattributes to tell the server which verb should be used to override the POSTmethod.


POST /api/Person/4 HTTP/1.1  
X-HTTP-Method-Override: PUT

In the above code, X-HTTP-Method-Overridethe method for specifying this request is PUT, not POST.

1.3 The object must be a noun

The object is the URL of the API and is the object of the HTTP verb. It should be a noun, not a verb. For example, /articlesthis URL is correct, but the URL below is not a noun, so it is all wrong.

  • / getAllCars
  • /createNewCar
  • /deleteAllRedCars

1.4 Plural URL

Since URL is a noun, should it be plural or singular?

There is no uniform rule, but a common operation is to read a collection, such as GET /articles(read all articles), which obviously should be plural.

For the sake of consistency, it is recommended to use plural URLs, such as GET /articles/2better than GET /article/2.

1.5 Avoid multi-level URLs

A common situation is that resources require multi-level classification, so it is easy to write a multi-level URL, such as obtaining a certain type of article by a certain author.


GET /authors/12/categories/2

This kind of URL is not conducive to expansion, and the semantics are not clear. It often takes a while to understand the meaning.

It is better to use query strings for all levels except the first level.


GET /authors/12?categories=2

Here is another example to query published articles. You may design the following URL.


GET /articles/published

The query string is significantly better written.


GET /articles?published=true

Second, the status code

2.1 The status code must be accurate

For every request from the client, the server must respond. The response includes two parts: HTTP status code and data.

The HTTP status code is a three-digit number divided into five categories.

  • 1xx:Related Information
  • 2xx:Successful operation
  • 3xx: Redirect
  • 4xx: Client error
  • 5xx:Server Error

These five categories contain a total of more than 100 status codes, covering most of the possible situations. Each status code has a standard (or agreed) interpretation. The client can determine what happened only by looking at the status code, so the server should return the status code as accurate as possible.

API does not require 1xxstatus codes. The precise meanings of the other four types of status codes are described below.

2.2 2xx status codes

200The status code indicates that the operation was successful, but different methods can return a more accurate status code.

  • GET: 200 OK
  • POST: 201 Created
  • PUT: 200 OK
  • PATCH: 200 OK
  • DELETE: 204 No Content

In the above code, the POSTreturn 201status code indicates that a new resource is generated; the DELETEreturn 204status code indicates that the resource no longer exists.

In addition, the 202 Acceptedstatus code indicates that the server has received the request, but has not yet processed it, and will process it in the future, usually for asynchronous operations. Below is an example.


HTTP/1.1 202 Accepted

{
  "task": {
    "href": "/api/company/job-management/jobs/2130040",
    "id": "2130040"
  }
}

2.3 3xx status codes

API does not use 301status code (permanent redirect) and 302status code (temporary redirect, which 307is also the meaning), because they can be returned by the application level, and the browser will jump directly. The API level does not need to consider these two cases.

The 3xxstatus code used by the API , mainly 303 See Other, refers to another URL. It 302and 307the meaning, just as "temporary redirect," The difference is that 302, and 307for the GETrequest, and 303for POST, PUTand DELETErequests. After receiving 303it, the browser will not automatically jump, but will let the user decide what to do next. Below is an example.


HTTP/1.1 303 See Other
Location: /api/orders/12345

2.4 4xx status codes

4xxThe status code indicates a client error, mainly as follows.

400 Bad Request: The server did not understand the client's request and did not do any processing.

401 Unauthorized: The user did not provide authentication credentials or did not pass authentication.

403 Forbidden: The user has passed the authentication, but does not have the necessary permissions to access the resource.

404 Not Found: The requested resource does not exist or is unavailable.

405 Method Not Allowed: The user has been authenticated, but the HTTP method used is not within his authority.

410 Gone: The requested resource has been transferred from this address and is no longer available.

415 Unsupported Media Type: The return format requested by the client is not supported. For example, the API can only return JSON format, but the client requires XML format.

422 Unprocessable Entity : The attachment uploaded by the client cannot be processed, causing the request to fail.

429 Too Many Requests: The number of client requests exceeds the limit.

2.5 5xx status codes

5xxThe status code indicates a server error. Generally speaking, the API does not disclose the detailed information of the server to the user, so only two status codes are enough.

500 Internal Server Error: The client request is valid, and an accident occurred during the server processing.

503 Service Unavailable: The server cannot process the request, it is generally used for website maintenance status.

Three, server response

3.1 Don't return to pure text

The data format returned by the API should not be a plain text, but a JSON object, because in this way can it return standard structured data. Therefore, the Content-Typeattributes of the HTTP header of the server response should be set application/json.

When the client requests it, it must also clearly tell the server that it can accept JSON format, that is, the ACCEPTattributes of the HTTP header of the request should also be set application/json. Below is an example.


GET /orders/2 HTTP/1.1 
Accept: application/json

3.2 When an error occurs, do not return a 200 status code

An inappropriate approach is to return the 200status code even if an error occurs, and put the error message in the data body, as shown below.


HTTP/1.1 200 OK
Content-Type: application/json

{
  "status": "failure",
  "data": {
    "error": "Expected at least two items in list."
  }
}

In the above code, after parsing the data body, the operation failed can be known.

This approach actually cancels the status code, which is completely undesirable. The correct approach is that the status code reflects the error that occurred, and the specific error information is returned in the data body. Below is an example.


HTTP/1.1 400 Bad Request
Content-Type: application/json

{
  "error": "Invalid payoad.",
  "detail": {
     "surname": "This field is required."
  }
}

3.3 Provide links

The user of the API may not know how the URL is designed. One solution is to provide relevant links in the response to facilitate the next step. In this case, users only need to remember one URL, and they can discover other URLs. This method is called HATEOAS.

For example, all GitHub APIs are in   the domain name api.github.com . By visiting it, you can get other URLs.


{
  ...
  "feeds_url": "https://api.github.com/feeds",
  "followers_url": "https://api.github.com/user/followers",
  "following_url": "https://api.github.com/user/following{/target}",
  "gists_url": "https://api.github.com/gists{/gist_id}",
  "hub_url": "https://api.github.com/hub",
  ...
}

In the above response, choose a URL to visit and you can get another URL. For users, there is no need to remember the URL design, just look it up step by step from api.github.com.

The format of HATEOAS is not uniformly regulated. In the above example, GitHub puts them together with other attributes. It would be better to separate related links from other attributes.


HTTP/1.1 200 OK
Content-Type: application/json

{
  "status": "In progress",
   "links": {[
    { "rel":"cancel", "method": "delete", "href":"/api/status/12345" } ,
    { "rel":"edit", "method": "put", "href":"/api/status/12345" }
  ]}
}

Four, reference link

(Finish)

Guess you like

Origin blog.csdn.net/gouguofei/article/details/103187873