使用REST風格架構您需要知道的一些事

1. REST的由來

REST即表述性狀態傳遞(英文:Representational State Transfer,簡稱REST)是Roy Fielding博士在2000年他的博士論文中提出來的一種軟件架構風格。

上世紀90年代面對高速發展的互聯網規模,HTTP1.0需要進一步改進。Roy Fielding們著手制定HTTP1.1的標準及后續擴展工作。HTTP1.1重視降低WEB系統開發的復雜性(通過增強HTTP的請求頭和響應頭),提高系統的可擴展性(通過更容易的緩存指令)以及其他性能優化工作(比如長連接和多個請求和響應可以重疊等)。

Roy Fielding在制定HTTP時有一個愿景:Web世界的應用程序應隨著不斷的超連接跳轉來實現應用系統狀態遷移,所以HTTP應該是一個應用協議,而不是一個純粹的超文本傳輸。

這就是REST的由來。當我們在談論REST的時候,表示我們在談論Web世界的應用一種基于HTTP的架構風格。

2. REST的構成

2017-12-10-20-52-26

3. 資源

在restful中資源是核心抽象,任何會被互聯網組件訪問的信息都是資源,并用一個URL/URN來標識。
舉例來說,獲取某網站的2017年10月1號的天氣信息,該網站可以命名改信息為http://www.somesite.com/weather/2017/10/1或者
http://www.somesite.com/weather?year=2017&month=10&day=1??蛻舳藶g覽器能用GET方法合法的獲取該資源。

如果天氣采集人員要創建2017年10月1號的天氣信息,則用POST方法提交表單給http://www.somesite.com/weather完成創建資源工作。
http://www.somesite.com/weather并沒有制定哪一天的天氣信息,但它確實資源,這體現資源的抽象性。

2017-12-05-22-08-41

4. 資源的表述

資源的表述是指資源的表現形式,這些形式由請求方和資源提供方通過HTTP協商指定。包括以下內容:

5. MIME(Multipurpose Internet Mail Extensions)

MIME是多用途互聯網郵件擴展類型,它是一個互聯網標準,擴展了電子郵件標準,使其能夠支持:
非ASCII字符文本;非文本格式附件(二進制、聲音、圖像等);由多部分(multiple parts)組成的消息體;包含非ASCII字符的頭信息(Header information)。

比如下圖,客戶端表示能接受json(首選),text(次選)以及任意格式(再次選);服務器端返回json內容給客戶端:

2017-12-06-20-54-01

6. 緩存約定

所以的資源操作包括讀取和更新操作,對于不頻繁更新的數據數據多數可以進行緩存。這種換成越靠近客戶端,用戶體驗越好,即提高了整體系統的可用性。
HTTP采取多層緩存機制,系統可以定義自己的緩存策略。(此處是否需要講公共緩存,私有緩存,運行機制?)

2017-12-06-21-30-01

其中代理服務器和緩存服務器應該只對公共緩存表述進行緩存,瀏覽器緩存對公共和私有的緩存表述都能進行緩存。通常代理服務器的緩存行為是用戶所屬組織支持的,不屬于應用系統的行為。

7. 資源的自描述

資源的自描述是指:資源的表述里面應該包括資源當前狀態的描述,以及對該資源或相關資源進一步操作的超鏈接。

8. 資源的當前狀態

資源的當前狀態由以下幾項共同組成:

  1. 屬于該資源的信息項目的值,比如訂單的編號,創建日期。
  2. 相關資源的鏈接,比如訂單的客戶鏈接以及訂單明細鏈接。
  3. 表示資源將來會遷移到某種可能狀態的鏈接,比如遷移到完成狀態的鏈接:/order/1/completeness POST
  4. 對應該資源與其他資源相關聯的任何業務規則的求值結果,比如訂單統計表:/order/statistics/year/2017 GET

下圖是一個訂單狀態的json表述:

2017-12-06-22-29-15

9. 操作資源的統一接口

HTTP的初衷是應用層協議,HTTP是REST風格的。HTTP的動作提供了操作字體的統一接口。

動作 接口作用 重復操作效果
POST 創建資源 不冪等
PUT 整體更新資源 冪等
PATCH 部分更新資源 不冪等
DELETE 刪除資源 冪等
GET 獲取資源 冪等

冪等 表示動作的重復執行不會再產生副作用(引起資源狀態變化),比如刪除一個資源后再次刪除也不會產生作用,同時系統也不應該返回錯誤信息,而是總是返回成功。

RPC或者SOAP風格的架構下HTTP是作為傳輸協議使用。

10. 請求的無狀態

REST的無狀態是指客戶端請求服務器時,應提供足夠的信息以讓服務器能理解并提供服務。無狀態的好處包括:

  1. 改善可見性(監視系統不必為了確定一個請求的全部性質而去查看請求之外的其他請求)
  2. 改善可靠性(減輕了從局部故障中恢復的任務量)
  3. 改善可伸縮性(服務端不必在多個請求直接保存狀態,從而允許服務器迅速釋放資源)

缺點:

  1. 由于服務器不能保持會話狀態數據,則會造成在每一次請求中發送大量重復的數據,可能會降低網絡性能。

下圖是請求有狀態和無狀態的對比例子:

2017-12-10-21-32-05

11. HATEOAS

HATEOAS(The Hypermedia As The Engine Of Application Statue),中文意思是“將超媒體作為應用狀態的引擎”,這是REST的最高目標(也叫主要架構約束)。

HATEOAS包括兩個概念:

  1. 應用狀態由應用(系統)中的各資源狀態組成,資源狀態的變化導致應用狀態的變化。
  2. 通過在資源表述中添加狀態遷移的超鏈接引導客戶端改變資源狀態。

比如:銷售訂單在創建后,客戶端通過GET操作獲取一個訂單信息,然后請求“審批訂單”鏈接使訂單變成“已審批“狀態??蛻舳嗽僬埱蟆眻绦杏唵巍巴瓿捎唵?。這就是一個簡單工作流程。

2017-12-07-21-38-33

12. REST與分布式事物

分布式系統中事物是一個重要話題,遺憾的是REST作為一種系統風格,并沒有約定對事物管理進行規定。事物是服務器端的事情,不論采用何種事物處理方式都要避免對客戶使用rest服務的影響。

13. REST的典型應用案例

1. GitHub Developer API

比如API:列出pull的評論

GET /repos/:owner/:repo/pulls/:number/reviews

2017-12-11-22-28-06

官網: https://developer.github.com/v3/pulls/reviews/

2. LinkIn 開發者中心

比如API:獲取當前用戶的信息

GET /v1/people/~?

2017-12-11-22-47-34

官網:https://developer.linkedin.com/zh-cn/docs/rest-api

14. REST vs RPC

REST式的Web服務和RPC式的Web服務在接口定義上的區別是,REST使用HTTP通用方法作為統一接口的標準詞匯,REST式的Web服務所提供的方法信息都在HTTP方法里,而RPC式的web服務所提供的方法信息在SOAP/HTTP信封里(其封裝的格式通常是HTTP或者是SOAP),每個RPC式的web服務都會公布一套符合自己商業邏輯的方法詞匯。

RPC的典型案例

1. 百度lbs服務API

比如API: 行政區劃區域檢索,之所以是rpc,是由于:

  1. 在參數中指定了資源格式MIME(此例是json),就是說資源表述由百度官方自定義協議解釋。
  2. 返回狀態和錯誤信息封裝在返回結果中,說明對于錯誤處理也由百度官方自定義協議解釋。
  3. 返回結果關心的是滿足當前接口數據,如果想進一步了解街道信息,客戶端須根據獲取街道信息API定義獲取。

http://api.map.baidu.com/place/v2/search?query=ATM機&tag=銀行&region=北京&output=json&ak=您的ak GET

2017-12-13-21-28-24

如果經過rest風格改造,行政區劃區域檢索API的返回結果可以是如下形式:

2017-12-14-22-15-45

注:百度lbs不是面向應用狀態遷移設計,因此采用rpc也是合適的。

2.Saleforce SOAP API

Saleforce提供了SOAP(簡單對象訪問協議) API,SOAP 通過發布WSDL(網絡服務描述語言)文件來描述服務器提供的API的輸入參數結構和返回數據結構以及可能的異常信息??蛻舳送ㄟ^WSDL生成客戶端調用代碼(SOAP語言無關,可跨開發語言調用),就能調用遠程的服務API。

下圖表示表示了Saleforce的提供的API的WSDL:

2017-12-13-22-21-31

注:Saleforce也提供了REST的API。

以下是二者的主要區別:

REST RPC
HTTP協議地位 應用協議 傳輸協議或者不用
傳輸協議 HTTP HTTP或者TCP
消息序列化類型 MIME MIME或者自定義協議
傳輸性能
服務處理性能
接口特點 通用(HTTP動作) 自定義接口動作
應用協議 HTTP 自定義
應用狀態遷移方式 資源狀態變化 業務數據狀態變化
緩存擴展性 自定義
客戶端耦合力度(協議)
客戶端代碼執行 按需提供(JS,CSS,HTML等) 默認不支持
客戶端的庫支持 不需要 最好有,且和服務同步升級
防火墻穿透力 默認不支持
公網組件支持度 現成支持,包括(反向)代理服務器,防火墻,緩存服務器,用戶代理(瀏覽器等) 需自行支持(http傳輸除外)
企業應用標準化程度 低(企業自定義) 中(基于SOAP協議,各廠商產品容易集成)

以下是主流RPC和REST框架

框架 特點 開發語言
Thrift Thrift是一個跨語言的RPC框架,自帶的代碼生成引擎大幅提高了開發效率,從而使它如此流行。
最初由Facebook團隊設計開發,現在已貢獻給Apache
多語言
Dubbo Dubbo是阿里巴巴開源的專門為Java設計的、成熟的RPC框架。支持基本的服務治理,所有服務治理
功能均在Client端集成:服務發現、負載均衡、容錯、監控等
Java
Spring HATEOAS Spring HATEOAS 可以很方便創建 基于HATEOAS 原則的REST 風格接口 ,
但需要依賴于 Spring 和 Spring MVC
Java

15. 總結

HTTP的本意是方便應用系統實現REST的架構,不過人們在早期并沒有意識到它的優點,因此目前更多使用的是RPC框架,因為REST 對開發人員的能力要求更高。綜上,REST具有以下主要特點:

  1. 以HTTP為應用協議。
  2. 基于WEB中間件進行擴展:緩存代理提高緩存擴展,反向代理提供負載均衡和內外網協議轉化(HTTPS和HTTP之間)。
  3. 請求的無狀態:由于服務器沒有會話上下文信息,提高系統的可伸縮性。缺點是傳輸冗余一些。
  4. 多級緩存:客戶端代理,代理服務器,緩存服務器提供了強大緩存能力,提高了系統的可用性。
  5. 對資源內容的描述方式,比如MIME協商或者在此基礎上的擴展格式,保證了系統的簡單性和通用性。
  6. 資源狀態變化促成應用狀態遷移(HATEOAS),可使開發者以資源為中心建模,這種設計相對簡單。
  7. 資源表述中鏈接廣告了應用的狀態流,但并不強迫客戶端進行處理,有利于客戶端平滑升級。
最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。