1. 程式人生 > >RESTful架構與RESTful API設計

RESTful架構與RESTful API設計

一、REST的由來

  REST這個詞是Roy Thomas Fielding博士在他2000年的博士論文中提出的,Fielding將他對網際網路軟體的架構原則定名為REST,即Representational State Transfer的縮寫,翻譯為“表現層狀態轉化”。如果一個架構符合REST原則,就稱它為RESTful架構,即REST風格的架構。

二、REST是什麼

  REST是一種架構風格,而不是一種架構。要理解RESTful架構,最好的方法就是去理解Representational State Transfer這個詞到底是什麼意思,他的每一個詞代表什麼含義。如果你把這個名詞搞懂了,就不難體會REST是一種什麼樣的設計。

資源(Resources)

  REST的名稱“表現層狀態轉化”中省略了主語。“表現層”其實是指的“資源(Resources)”的“表現層”。
  所謂“資源”,就是網路上的一個實體,或者是網路上的一個具體資訊。它可以是一段文字、一張圖片、一首歌曲、一種服務、總之就是一個具體的實體。你可以用一個URI(統一資源識別符號)指向它,每種資源對應一個特定的URL。要獲取這個資源,訪問它的URI就可以,因此URI就成了每一個資源的地址或獨一無二的識別符。

表現層(Representation)

  “資源”是一種資訊實體,他可以有多種的外在表現形式。我們把“資源”具體呈現出來的形式稱之為“表現層”

。比如:文字可以用txt格式表現,也可以用HTML格式、XML格式、JSON格式表現,甚至可以採用二進位制格式表現;圖片可以採用JPG格式表現,也可以用PNG格式表現。
  URI只代表資源的實體,不代表他的形式。嚴格地說,有些網址最後的“.html”字尾名是不必要的,因為這個字尾名錶示格式,屬於“表現層”的範疇,而URI應該只代表“資源”的位置。它的具體表現形式應該在HTTP請求的頭資訊中用Accept和Content-Type欄位指定,這兩個欄位才是對“表現層”的描述,不過在大部分應用中,通過後綴區分表現層就已經足夠了。

狀態轉化(State Transfer)

  訪問一個網站,就代表了客戶端和伺服器的一個互動過程。在這個過程中,勢必涉及資料和狀態的變化。
  HTTP協議是一個無狀態網際網路通訊協議,這意味著所有狀態都儲存在伺服器端。因此,如果客戶端想要操作伺服器,必須通過某種手段,讓伺服器發生“狀態轉化(State Transfer)”。而這種轉化是建立在表現層之上的,所以就叫做“表現層狀態轉化”。


  客戶端用到的手段只能是HTTP協議。具體的說,HTTP協議裡有5個常用的表示操作方式的動詞:GET、POST、PUT、DELETE、PATCH。它們分別對應5種基本操作:GET用來獲取資源,POST用來新建資源(也可以用來更新資源),PUT用來更新資源,DELETE用來刪除資源,PATCH用來更新資源的部分屬性。

三、RESTful架構

  現在流行的各種Web框架,包括Spring Boot都支援REST開發,REST並非是一種技術或者規範,而是一種架構風格,這種架構風格逐漸各種程式語言的Web框架所支援。它包括了REST架構中如何標識資源,如何表示操作介面及操作版本,如何標識操作結果等,主要內容如下:

  • 使用“api”作為Web上下文;
  • 增加版本標識;
  • 標識資源;
  • REST中的HTTP Method;
  • REST中的HTTP Status;

1)使用“api”作為上下文:

http://192.168.0.1/api

  也有的使用“api”作為二級域名:

http://api.XXXX.com

2)增加一個版本標識

http://192.168.0.1/api/v1.1

  也有的做法是將版本資訊放到HTTP頭,但這裡推薦還是通過URl來實現,這樣使得REST的相關程式碼更加容易閱讀。

3)標識資源

  將資源名稱放到URL中,如果資源有層級關係,則放入層級關係:

http://192.168.0.1/api/v1.1/user

  如果使用者屬於系統管理,也可以這麼寫:

http://192.168.0.1/api/v1.1/system/user

4)確定HTTP Method

  在REST中,HTTP Method常常對應一下含義:

  • POST:代表增加資源;
  • PUT:代表更改資源,客戶端提供完整的資源屬性;
  • GET:代表查詢資源;
  • PATCH:更新資源,客戶端提供僅需要更改的資源屬性;
  • DELETE:通常用於刪除資源;
  • HEAD:類似GET,但僅僅只有HTTP頭資訊,頭資訊中包含了需要查詢的資訊;
  • OPTIONS,用於獲取URI所支援的方法,相應資訊會在HTTP頭中包含一個名為“Allow”的頭,值是所支援的方法,如“GET、POST”;

在業務系統中,刪除往往並不是指的物理刪除,而是邏輯刪除,資源通常仍在資料庫中,只是狀態設定為刪除狀態。

RESTful API設計的一些例子
新增使用者:

POST:http://192.168.0.1/api/v1.1/system/user

查詢id為45的使用者

GET:http://192.168.0.1/api/v1.1/system/user/45

查詢所有使用者:

GET:http://192.168.0.1/api/v1.1/system/user

如果有翻頁,可以在後面增加類似offset、limit引數,比如:

GET:http://192.168.0.1/api/v1.1/system/user?offset=1&limit=20&sortBy=name

更新使用者id為45的使用者:

PUT:http://192.168.0.1/api/v1.1/system/user/45

刪除使用者id為45的使用者:

DELETE:http://192.168.0.1/api/v1.1/system/user/45

注意:可以為資源標識新增字尾,使得REST程式碼更加容易閱讀,比如:

GET: http://192.168.0.1/api/v1.1/system/user/45.json

返回id為45的使用者資訊,返回格式是json

5)確定HTTP Status

  伺服器向客戶端返回HTTP Status以表示操作是否成功,常用的如下:

  • 200,OK,使用者請求成功,如查詢資料成功返回。
  • 400,錯誤的請求。
  • 404 ,NOT Found,使用者發出的請求針對的資源不存在,通常是Spring Boot中的Controller沒有匹配上URI,或者匹配上了Controller方法,但是渲染的檢視不存在。
  • 405,用來訪問本頁面的HTTP Method不被允許。
  • 406,表示無法使用請求的內容特性來相應請求資源,比如在Spring Boot中,請求字尾以html結尾,但同時請求的HTTP頭中又包含Accept:application/json。
  • 500,伺服器內部錯誤,無法完成請求,通常是Controller丟擲的異常。

四、RESTful總結

  1)每一個URI代表一種資源
  2)客戶端和伺服器之間傳遞這種資源的表現層
  3)客戶端通過HTTP動詞,對伺服器端資源進行操作,實現“表現層狀態轉化”。
  一句話概括:URI定位資源,用HTTP動詞(GET,POST,DELETE,DETC)描述操作。

五、REST VS. WebService

  REST和WebService主要的差別就是前者是一種輕量級的架構,而後者是一種重量級架構。前者即適合終端到服務的呼叫,系統內部子系統的互相呼叫,也適合不同公司之間的系統互相呼叫,而WebService較為適合不同公司之間系統的呼叫。
  注:有不明白WebService的同學請看下面的參考資料。

六、參考資料

  理解RESTful架構
  RESTful API 設計指南
  
  有關WebService的文章:
  Web service是什麼?
  Web Service技術的SOAP實現
  Web Services 系列教程
  Web API知識
  到底 REST 和 SOAP、RPC 有何區別?