SlideShare une entreprise Scribd logo
1  sur  57
Télécharger pour lire hors ligne
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
RESTful API DesignRESTful API Design
Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
特別感謝
●
感謝 Mozilla 借出場地
●
感謝陳兆祥先生幫助活動統籌
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
大綱
●
個人簡述
●
為什麼要重視 API 設計
●
比較傳統與 API 網頁設計
●
RESTful API 設計
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
大綱
●
個人簡述
●
為什麼要重視 API 設計
●
比較傳統與 API 網頁設計
●
RESTful API 設計
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
個人簡述
●
豐富的火星系統救火經驗
●
喜歡資料庫
●
喜歡貓
●
出沒於 Hong Kong Linux User Group @ FB
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
大綱
●
個人簡述
●
為什麼要重視 API 設計
●
比較傳統與 API 網頁設計
●
RESTful API 設計
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
為什麼要重視 API 設計
好的 API 設計,
不能讓你考試一百分,升職加薪
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
但是可以讓你減少爆肝機會
(前題:老闆在你提升工作效率後不再追加工作)
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
大綱
●
個人簡述
●
為什麼要重視 API 設計
●
比較傳統與 API 網頁設計
●
RESTful API 設計
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
誰需要重視 API 設計
等一下,我是網頁工程師
RESTful API 和我有關係嗎?
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
傳統網頁流程
Client Server
1. 用戶發出 http://www.abc.com 的 Request
2. 伺服器根據準備 Data 和 Presention logic
Presentation
Code
4. 伺服器把 html 丟回用戶
Data
3. 伺服器把 Data 和 Presentation 結合成完整的 html
Result html
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
可怕的程式碼與數據交錯
●
Data 和 Presentation 混合, Presentation 無法單
獨 cache ,只要 Data 變動就必須重新產生
●
無法徹底分割 Presentation 、 Business Logic 、
和 Data ,影響開發、測試、除錯的協同作業
●
伺服器負責將 Data 和 Presentation 整合(簡稱
Data Binding ),消耗伺服器的 CPU 資源
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
API 網頁工程師的看法
Client Server
1. 用戶發出 http://www.abc.com 的 Request
2. 伺服器回傳 Presentation 文件與 Scripting 檔案
Presentation
Code
Script
Code
3. 用戶端瀏覽器執行 Scripting ,根據指示對 api.opensource.hk 作出 request
4. 伺服器以 json / xml 的格式回傳 Data
Data
5. 瀏覽器把 html 和 Data 結合,然後在畫面顯示出來
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
優點 1 :客戶端快取節省流量
表面上看起來,原先僅需一次 request 增加為兩次,
似乎花了更多的時間與網路流量!
但是,只要負責美工的同事不改變網頁外表。第一個
request 伺服器會回答 HTTP 304 Not Modified ,直
譯就是:回家吃自己~ Presentation 最近沒改動,用
之前的版本吧!
因為網頁的 Presentation 不用每次重傳,可以節省不
少網路流量(=省下錢$)
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
優點 2 :資料與介面分離
現在 Presentation 和 Data 已經徹底分離!
開發和測試 Presentation 的 data mocking 可以使用
專門的 mock API 伺服器。
只要準備好 API 與測試資料,前端工程師就能專心工
作。前端延誤和後端工程師無關,不必背黑鍋~
可再將執行架構改為 Presentation 在 Apache , API
在 Tomcat 。
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
優點 3 :節省伺服器計算資源
可以不在伺服器做的東西,便不要放在伺服器
Data Binding 現在是交給瀏覽器處理,不再是伺服器
的工作,省下伺服器的 CPU 計算資源 !
即使未來要支持 IOS , Android ,只要背後邏輯不
變,這些 API 將能全部重覆使用,節省開發時間!
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
優點4:能重用的伺服器程式
即使未來要支持 IOS , Android ,只要背後邏
輯不變,這些 API 將能全部重覆使用,節省開
發時間
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
大綱
●
個人簡述
●
為什麼要重視 API 設計
●
比較傳統與 API 網頁設計
●
RESTful API 設計
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
先談 RESTful 謬誤
server side 需要 stateless
正解: RESTful 只要求 Application Server 是
stateless , Server Side 其他部份可以 stateful
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
要新一代支援 RESTful 的 noSQL 資料庫
正解: RESTful 和資料庫沒直接關係,你可以使用
PostgreSQL 、 MySQL 、或 Oracle
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
一定需要用上 HTTP 的 GET, PUT, POST, DELETE
正解:統一介面 (Uniform interface) 只建議善用
HTTP ,使用其他技術實作的統一介面也能滿足
RESTful 要求
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
使用 RESTful 的工程師都找不到女朋友
正解:(這倒有可能是事實)
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
RESTful 的要求
●
Client-server (客戶端和伺服器結構)
●
Cacheable (能夠利用快取機制增進性能)
●
Layered system (分層式系統)
●
Stateless protocol (通訊協定具有無狀態性)
●
Uniform interface (統一介面)
From Wiki
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
RESTful 的要求
●
Client-server (客戶端和伺服器結構)
●
Cacheable (能夠利用快取機制增進性能)
●
Layered system (分層式系統)
●
Stateless protocol (通訊協定具有無狀態性)
●
Uniform interface (統一介面)
From Wiki
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
客戶端和伺服器結構
●
滿足 RESTful 的系統必需存在客戶端和伺服器端
●
RESTful 只規範伺服器,和客戶端與伺服器端之
間的通訊協定
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
RESTful 的要求
●
Client-server (客戶端和伺服器結構)
●
Cacheable (能夠利用快取機制增進性能)
●
Layered system (分層式系統)
●
Stateless protocol (通訊協定具有無狀態性)
●
Uniform interface (統一介面)
From Wiki
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
能夠利用快取機制增進性能
●
系統內的所有東西都必須定義能否使用快取
●
客戶端可以為首次可快取資源建立本地快取!在
下次 Request 時,客戶會把本地快取版本告訴伺
服器。如果伺服器發現資源沒有改動,便會要求
客戶端使用本地快取的資源。
●
可以省下伺服器 CPU 資源和網路流量(=省錢)
●
不常變動的物件適合設定為可快取,如網頁界面
●
詳見: HTTP conditional GET
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
RESTful 的要求
●
Client-server (客戶端和伺服器結構)
●
Cacheable (能夠利用快取機制增進性能)
●
Layered system (分層式系統)
●
Stateless protocol (通訊協定具有無狀態性)
●
Uniform interface (統一介面)
From Wiki
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
分層式系統
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
RESTful 的要求
●
Client-server (客戶端和伺服器結構)
●
Cacheable (能夠利用快取機制增進性能)
●
Layered system (分層式系統)
●
Stateless protocol (通訊協定具有無狀態性)
●
Uniform interface (統一介面)
From Wiki
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
以下內容非常重要,直接影響到閣下未來爆肝度
睡著了的朋友請起來聽講
(謎之聲:睡了的朋友又怎能看到這段文字?)
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
淺談網路的不穩定性
●
隨時會斷線!往往看起來正常,其實已經斷線
●
使用 API 時,連線可能在信號送達伺服器前斷線
●
也可能在伺服器正要傳回 API 結果時斷線
●
更可能客戶端以為斷線,卻早已成功傳送資訊
●
除非使用同一個 TCP/IP 連線,否則當客戶端先
發出 API1 ,然後再發出 API2 後,在次序錯亂的
情況下,伺服器有可能先收到 API2 ~
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
無狀態通訊協定
1. 通訊協定具有無狀態性
2. atomic (原子)
3. 足夠完整的資料
4. 重新呼叫
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
無狀態通訊協定
1. 通訊協定具有無狀態性
2. atomic (原子)
3. 足夠完整的資料
4. 重新呼叫
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
通訊協定具有無狀態性
RESTful 伺服器端是被允許有狀態的
Application Server 必須是無狀態
RESTful 准許把狀態儲存到資料庫中,例如將登入狀
態的短期資訊放到短期資料庫 (Redis)
最簡單的程式說法: RESTful 禁止使用
HttpSession(Java) , session_start(PHP)
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
無狀態通訊協定範例
1. 用戶發出 http://api.abc.com/user/60321?access-
key=rbo9PUDgx3Bvl5Ij20fYEWct_CfH
2. Application Server 對 access-key 作出解密,得
到 Session ID=0x1A6C9C77869EF675
3. Application Server 根據 Session ID ,到 Redis
資料庫拿回登入狀態,知道用戶正是 User 60321
本人,並且有足夠權限使用這個 API
4. Application Server 到 PostgreSQL 資料庫拿資料
5. Application Server 把資料以 JSON 格式傳回用戶
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
無狀態通訊協定
1. 通訊協定具有無狀態性
2. atomic (原子性)
3. 足夠完整的資料
4. 重新呼叫
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
atomic (原子性)
每一個動作都必需是 atomic 。一個完整執行後的
API 呼叫不能讓伺服器端數據停留在不一致的狀態。
Each action call should be atomic. Any Successful
API call should not leave server side in inconsistent
state.
另一個說法:你不能使用二個(或以上) API 呼叫去
完成一個「動作」
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
不符合 atomic 的範例
●
你現在是光明破壞神三的工程師,因為遊戲內有
檢錢這個動作,所以有檢錢的 API
/user/60321/single_user_coin_change (POST)
POST_DATA =
{
"change_amount": 100,
"description" : " 從怪物 645389890 的屍體上檢錢 ",
"create_time" : "2014-07-05T16:35:46"
}
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
●
現在主管突然覺得數字網太好賺,想連那部份也
自己來賺,要求讓遊戲中的金幣支援轉帳服務
●
主管說:不用新建 API 啦,把現有的
single_user_coin_change 沿用,把「用戶A轉帳
到用戶B」這個動作拆成「從用戶A扣錢」和
「把錢加到用戶B」二個動作。
看到不符合的地方嗎?
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
●
後果是:新的轉帳功能推出後,有用戶發現轉帳
時金幣不翼而飛!
●
因為用戶完成「從用戶A扣錢」後,遇上藍畫面
或是網絡問題,沒法完成「把錢加到用戶B」動
作。
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
前端工程師想出了解決方案:轉帳前先把這記錄存放
在客戶端硬碟
●
程式重新啟動時發現未完成的轉帳記錄時,客戶
端需要:
●
先問伺候器,轉帳過程是停在那一步驟
●
從當掉的步驟重來
不過對於硬碟故障的客戶,這方案沒用!
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
後端工程師想出了另一個解決方案:藉 POST_DATA
中的 description 作配對。
●
找出所有扣了A的錢而沒有為B加錢的轉帳,然
後作出數據回復
●
需要定期掃瞄資料庫中的所有記錄,引起嚴重效
能問題
掃瞄程式超級難寫,後端工程師肝病可能性大升
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
符合 atomic 的範例
●
建立新的 API
RESTful API /user/{user_id}/coin_transfer_transaction (POST)
POST_DATA =
{
"from_user_id": "60321",
"to_user_id": "89072",
"amount": 100,
"description" : " 從用戶 60321 轉帳到用戶 89072"
"create_time" : "2014-07-05T16:35:46"
}
當用戶當機或網路斷線,再重新執行一次 API 即可!
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
無狀態通訊協定
1. 通訊協定具有無狀態性
2. atomic (原子)
3. 足夠完整的資料
4. 重新呼叫
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
足夠完整的資料
每個 API 呼叫時都需要向伺服器提供足夠完整的資料
Each API call should provide sufficient information
for server side to process.
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
常見錯誤
●
你不應該假設伺服器知道「現在狀態」
錯誤例子:玩中國象棋時,單純把用戶端指令用「炮
二平五」來回傳給伺服器
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
不完整的資料範例
1. 在紅方第 31 步行動時,紅方發出「炮二平五」指令
2. 這時網絡某個路由器發生嚴重錯亂,把「炮二平五」的網
絡封包送到火星
3. 紅方電腦等 10 秒後沒有收到伺服器回應,以為網絡錯
誤,於是再發出「炮二平五」指令,這個封包經由正常的
路由器,所以 1 秒內就被傳送到伺服器
4. 10 分鐘後,送往火星的錯誤封包終於被送到伺服器
5. 這時已經到達第 55 步紅方行動,剛好紅方有炮棋在二
線,伺服器沒法知道這是第 31 步時的封包,並且以為這
是第 55 步的指令,因此執行「炮二平五」的指令,並且
拒絕之後用戶真正第 55 步的指令
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
●
RESTful 的「足夠資料」,在中國象棋中最簡單
實現的方法便是把每隻棋子的位置以及棋局的最
後更改時間,在「炮二平五」的指令中同時傳給
伺服器。
●
這樣伺服器便有足夠資料去分辨第 31 步時路經火
星的封包。(因為棋局狀況和最後更改時間不符
合)
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
●
不過,每次都把完整狀態丟來丟去是白痴,因為
這將會大量消耗網絡封包
●
如果這是梭哈遊戲,你有機會可以攔截封包,事
先得知對手蓋牌,有資安疑慮!
所以:基於網路效能和資安考量, API 所用的資料可
以放在伺服器, API 只需說明正在引用那份資料。
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
完整的資料範例
/chinese_chess_game/{game_id} (PUT)
PUT_DATA =
{
"step_id" : 31
"action" : " 炮二平五 "
}
伺服器收到這個 Request 時,會從短期資料庫中拿
出第 31 步的棋局。
如果第 31 步已經被執行,伺服器會檢查已經存在的
第 31 步是否等於 " 炮二平五 " 。如果是,傳回"成
功"給客戶端;如果不是,則傳回錯誤。
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
無狀態通訊協定
1. 通訊協定具有無狀態性
2. atomic (原子)
3. 足夠完整的資料
4. 重新呼叫
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
重新呼叫
●
在客戶端,任何未成功收到傳回訊息的 API ,只
需要重新呼叫。
●
伺服器端需要懂得處理重覆 API request
●
在建立新物件時,把客戶端時間也放到 API
request 中,讓伺服器能分辦是否收到重覆的
HTTP POST
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
RESTful 的要求
●
Client-server (客戶端和伺服器結構)
●
Cacheable (能夠利用快取機制增進性能)
●
Layered system (分層式系統)
●
Stateless protocol (通訊協定具有無狀態性)
●
Uniform interface (統一介面)
From Wiki
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
統一介面
●
所有介面都應該基於物件,而不是行動
●
前述的遊戲檢錢,就是建立
single_user_coin_change 這個物件
●
一個物件正常有4種行動:查詢,更改,誕生,
刪除
●
查詢:一般使用 HTTP GET method
●
更改:一般使用 HTTP PUT method
●
誕生:一般使用 HTTP POST method
●
刪除:一般使用 HTTP DELETE method
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
統一介面範例
/v3/user/1234/book/54389
●
v3 = 使用第三版本的 /user/1234/book/54389 API
●
user/1234/book/54389 = 這是關於使用者 1234 屬下的書
本 54389
– GET = 取得書本內容
– PUT = 更改書本內容
– DELETE = 刪除書本紀錄
/v3/user/1234/book/
●
GET = 取得使用者 1234 屬下的書本
●
POST = 在使用者 1234 屬下建立新的書本
©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
問題時間

Contenu connexe

Tendances

RESTful services
RESTful servicesRESTful services
RESTful servicesgouthamrv
 
REST API Design & Development
REST API Design & DevelopmentREST API Design & Development
REST API Design & DevelopmentAshok Pundit
 
Rest presentation
Rest  presentationRest  presentation
Rest presentationsrividhyau
 
Learn REST in 18 Slides
Learn REST in 18 SlidesLearn REST in 18 Slides
Learn REST in 18 SlidesSuraj Gupta
 
OpenAPI at Scale
OpenAPI at ScaleOpenAPI at Scale
OpenAPI at ScaleNordic APIs
 
20220716_만들면서 느껴보는 POP
20220716_만들면서 느껴보는 POP20220716_만들면서 느껴보는 POP
20220716_만들면서 느껴보는 POPChiwon Song
 
Ch03 請求與回應
Ch03 請求與回應Ch03 請求與回應
Ch03 請求與回應Justin Lin
 
JavaScript Fetch API
JavaScript Fetch APIJavaScript Fetch API
JavaScript Fetch APIXcat Liu
 
What is REST API? REST API Concepts and Examples | Edureka
What is REST API? REST API Concepts and Examples | EdurekaWhat is REST API? REST API Concepts and Examples | Edureka
What is REST API? REST API Concepts and Examples | EdurekaEdureka!
 
Rest & RESTful WebServices
Rest & RESTful WebServicesRest & RESTful WebServices
Rest & RESTful WebServicesPrateek Tandon
 
Understanding REST APIs in 5 Simple Steps
Understanding REST APIs in 5 Simple StepsUnderstanding REST APIs in 5 Simple Steps
Understanding REST APIs in 5 Simple StepsTessa Mero
 
ASP.NET Core 6.0 全新功能探索
ASP.NET Core 6.0 全新功能探索ASP.NET Core 6.0 全新功能探索
ASP.NET Core 6.0 全新功能探索Will Huang
 
Introduction to REST - API
Introduction to REST - APIIntroduction to REST - API
Introduction to REST - APIChetan Gadodia
 
Javascript Module Patterns
Javascript Module PatternsJavascript Module Patterns
Javascript Module PatternsNicholas Jansma
 

Tendances (20)

RESTful services
RESTful servicesRESTful services
RESTful services
 
REST API Design & Development
REST API Design & DevelopmentREST API Design & Development
REST API Design & Development
 
RESTful API - Best Practices
RESTful API - Best PracticesRESTful API - Best Practices
RESTful API - Best Practices
 
Rest presentation
Rest  presentationRest  presentation
Rest presentation
 
Airflow and supervisor
Airflow and supervisorAirflow and supervisor
Airflow and supervisor
 
Rest API
Rest APIRest API
Rest API
 
Learn REST in 18 Slides
Learn REST in 18 SlidesLearn REST in 18 Slides
Learn REST in 18 Slides
 
Doing REST Right
Doing REST RightDoing REST Right
Doing REST Right
 
Spring batch overivew
Spring batch overivewSpring batch overivew
Spring batch overivew
 
OpenAPI at Scale
OpenAPI at ScaleOpenAPI at Scale
OpenAPI at Scale
 
20220716_만들면서 느껴보는 POP
20220716_만들면서 느껴보는 POP20220716_만들면서 느껴보는 POP
20220716_만들면서 느껴보는 POP
 
Ch03 請求與回應
Ch03 請求與回應Ch03 請求與回應
Ch03 請求與回應
 
REST & RESTful Web Services
REST & RESTful Web ServicesREST & RESTful Web Services
REST & RESTful Web Services
 
JavaScript Fetch API
JavaScript Fetch APIJavaScript Fetch API
JavaScript Fetch API
 
What is REST API? REST API Concepts and Examples | Edureka
What is REST API? REST API Concepts and Examples | EdurekaWhat is REST API? REST API Concepts and Examples | Edureka
What is REST API? REST API Concepts and Examples | Edureka
 
Rest & RESTful WebServices
Rest & RESTful WebServicesRest & RESTful WebServices
Rest & RESTful WebServices
 
Understanding REST APIs in 5 Simple Steps
Understanding REST APIs in 5 Simple StepsUnderstanding REST APIs in 5 Simple Steps
Understanding REST APIs in 5 Simple Steps
 
ASP.NET Core 6.0 全新功能探索
ASP.NET Core 6.0 全新功能探索ASP.NET Core 6.0 全新功能探索
ASP.NET Core 6.0 全新功能探索
 
Introduction to REST - API
Introduction to REST - APIIntroduction to REST - API
Introduction to REST - API
 
Javascript Module Patterns
Javascript Module PatternsJavascript Module Patterns
Javascript Module Patterns
 

Similaire à RESTful API Design

Res tful api design tw-2.0
Res tful api design tw-2.0Res tful api design tw-2.0
Res tful api design tw-2.0昀陞 李
 
災難演練 @ AWS 實戰分享 (Using AWS for Disaster Recovery)
災難演練 @ AWS 實戰分享 (Using AWS for Disaster Recovery)災難演練 @ AWS 實戰分享 (Using AWS for Disaster Recovery)
災難演練 @ AWS 實戰分享 (Using AWS for Disaster Recovery)Rick Hwang
 
Web server and_cgi
Web server and_cgiWeb server and_cgi
Web server and_cgixu liwei
 
轻量级Flash服务器开发框架(刘恒)
轻量级Flash服务器开发框架(刘恒)轻量级Flash服务器开发框架(刘恒)
轻量级Flash服务器开发框架(刘恒)FLASH开发者交流会
 
如何利用 OpenAPI 及 WebHooks 讓老舊的網路服務也可程式化
如何利用 OpenAPI 及 WebHooks 讓老舊的網路服務也可程式化如何利用 OpenAPI 及 WebHooks 讓老舊的網路服務也可程式化
如何利用 OpenAPI 及 WebHooks 讓老舊的網路服務也可程式化Mu Chun Wang
 
瀏覽器開發與開源經驗 COSCUP 2018
瀏覽器開發與開源經驗 COSCUP 2018瀏覽器開發與開源經驗 COSCUP 2018
瀏覽器開發與開源經驗 COSCUP 2018安齊 劉
 
柔性数据接口的设计与实现
柔性数据接口的设计与实现柔性数据接口的设计与实现
柔性数据接口的设计与实现Leo Zhou
 
Scaling Offline Database Usage On GCP @ Dcard
Scaling Offline Database Usage On GCP @ DcardScaling Offline Database Usage On GCP @ Dcard
Scaling Offline Database Usage On GCP @ DcardJui An Huang (黃瑞安)
 
瀏覽器與網頁原理 Principles of Browsers and Webpages
瀏覽器與網頁原理 Principles of Browsers and Webpages瀏覽器與網頁原理 Principles of Browsers and Webpages
瀏覽器與網頁原理 Principles of Browsers and Webpages安齊 劉
 
Python和web开发
Python和web开发Python和web开发
Python和web开发moonbingbing
 
100902 wm4wps-py-webdev
100902 wm4wps-py-webdev100902 wm4wps-py-webdev
100902 wm4wps-py-webdevZoom Quiet
 
http flood and mobile app
http flood and mobile apphttp flood and mobile app
http flood and mobile appim_yunshu
 
腾讯大讲堂58 拍拍app platform中间件解决方案简介
腾讯大讲堂58 拍拍app platform中间件解决方案简介腾讯大讲堂58 拍拍app platform中间件解决方案简介
腾讯大讲堂58 拍拍app platform中间件解决方案简介areyouok
 
腾讯大讲堂58 拍拍app platform中间件解决方案简介
腾讯大讲堂58 拍拍app platform中间件解决方案简介腾讯大讲堂58 拍拍app platform中间件解决方案简介
腾讯大讲堂58 拍拍app platform中间件解决方案简介George Ang
 
Http协议介绍
Http协议介绍Http协议介绍
Http协议介绍Sanji Zhang
 
Jira live demo_2020_v20
Jira live demo_2020_v20Jira live demo_2020_v20
Jira live demo_2020_v20Linktech
 
Accel_Series_2023Autumn_Zh.pptx
Accel_Series_2023Autumn_Zh.pptxAccel_Series_2023Autumn_Zh.pptx
Accel_Series_2023Autumn_Zh.pptxNTTDATA INTRAMART
 

Similaire à RESTful API Design (20)

Res tful api design tw-2.0
Res tful api design tw-2.0Res tful api design tw-2.0
Res tful api design tw-2.0
 
災難演練 @ AWS 實戰分享 (Using AWS for Disaster Recovery)
災難演練 @ AWS 實戰分享 (Using AWS for Disaster Recovery)災難演練 @ AWS 實戰分享 (Using AWS for Disaster Recovery)
災難演練 @ AWS 實戰分享 (Using AWS for Disaster Recovery)
 
災難演練@AWS 實戰分享
災難演練@AWS 實戰分享 災難演練@AWS 實戰分享
災難演練@AWS 實戰分享
 
Web server and_cgi
Web server and_cgiWeb server and_cgi
Web server and_cgi
 
轻量级Flash服务器开发框架(刘恒)
轻量级Flash服务器开发框架(刘恒)轻量级Flash服务器开发框架(刘恒)
轻量级Flash服务器开发框架(刘恒)
 
如何利用 OpenAPI 及 WebHooks 讓老舊的網路服務也可程式化
如何利用 OpenAPI 及 WebHooks 讓老舊的網路服務也可程式化如何利用 OpenAPI 及 WebHooks 讓老舊的網路服務也可程式化
如何利用 OpenAPI 及 WebHooks 讓老舊的網路服務也可程式化
 
瀏覽器開發與開源經驗 COSCUP 2018
瀏覽器開發與開源經驗 COSCUP 2018瀏覽器開發與開源經驗 COSCUP 2018
瀏覽器開發與開源經驗 COSCUP 2018
 
柔性数据接口的设计与实现
柔性数据接口的设计与实现柔性数据接口的设计与实现
柔性数据接口的设计与实现
 
Scaling Offline Database Usage On GCP @ Dcard
Scaling Offline Database Usage On GCP @ DcardScaling Offline Database Usage On GCP @ Dcard
Scaling Offline Database Usage On GCP @ Dcard
 
瀏覽器與網頁原理 Principles of Browsers and Webpages
瀏覽器與網頁原理 Principles of Browsers and Webpages瀏覽器與網頁原理 Principles of Browsers and Webpages
瀏覽器與網頁原理 Principles of Browsers and Webpages
 
Python和web开发
Python和web开发Python和web开发
Python和web开发
 
100902 wm4wps-py-webdev
100902 wm4wps-py-webdev100902 wm4wps-py-webdev
100902 wm4wps-py-webdev
 
http flood and mobile app
http flood and mobile apphttp flood and mobile app
http flood and mobile app
 
Python in vir
Python in virPython in vir
Python in vir
 
腾讯大讲堂58 拍拍app platform中间件解决方案简介
腾讯大讲堂58 拍拍app platform中间件解决方案简介腾讯大讲堂58 拍拍app platform中间件解决方案简介
腾讯大讲堂58 拍拍app platform中间件解决方案简介
 
Html5
Html5Html5
Html5
 
腾讯大讲堂58 拍拍app platform中间件解决方案简介
腾讯大讲堂58 拍拍app platform中间件解决方案简介腾讯大讲堂58 拍拍app platform中间件解决方案简介
腾讯大讲堂58 拍拍app platform中间件解决方案简介
 
Http协议介绍
Http协议介绍Http协议介绍
Http协议介绍
 
Jira live demo_2020_v20
Jira live demo_2020_v20Jira live demo_2020_v20
Jira live demo_2020_v20
 
Accel_Series_2023Autumn_Zh.pptx
Accel_Series_2023Autumn_Zh.pptxAccel_Series_2023Autumn_Zh.pptx
Accel_Series_2023Autumn_Zh.pptx
 

Plus de Amigo 陳兆祥

20140920 創業前要作的事
20140920 創業前要作的事20140920 創業前要作的事
20140920 創業前要作的事Amigo 陳兆祥
 
以Code igniter為基礎的網頁前端程式設計
以Code igniter為基礎的網頁前端程式設計以Code igniter為基礎的網頁前端程式設計
以Code igniter為基礎的網頁前端程式設計Amigo 陳兆祥
 
PHP CodeIgniter 框架之美
PHP CodeIgniter 框架之美PHP CodeIgniter 框架之美
PHP CodeIgniter 框架之美Amigo 陳兆祥
 
20140824 如何協助業務部門達成業績目標與更精準的預測
20140824 如何協助業務部門達成業績目標與更精準的預測20140824 如何協助業務部門達成業績目標與更精準的預測
20140824 如何協助業務部門達成業績目標與更精準的預測Amigo 陳兆祥
 
20140824 從離職到開始 crm 顧問的轉變
20140824 從離職到開始 crm 顧問的轉變20140824 從離職到開始 crm 顧問的轉變
20140824 從離職到開始 crm 顧問的轉變Amigo 陳兆祥
 
20140824 認識與應用商業模式
20140824 認識與應用商業模式20140824 認識與應用商業模式
20140824 認識與應用商業模式Amigo 陳兆祥
 
20140816 工程師要如何準備一場成功的簡報!
20140816 工程師要如何準備一場成功的簡報!20140816 工程師要如何準備一場成功的簡報!
20140816 工程師要如何準備一場成功的簡報!Amigo 陳兆祥
 
20140809 如何加速行銷部門作業流程與編列預算
20140809 如何加速行銷部門作業流程與編列預算20140809 如何加速行銷部門作業流程與編列預算
20140809 如何加速行銷部門作業流程與編列預算Amigo 陳兆祥
 
High Availability and High Performance Server Side
High Availability and High Performance Server SideHigh Availability and High Performance Server Side
High Availability and High Performance Server SideAmigo 陳兆祥
 
20140724 中小企業 QNAP Virtualization Station 快速導入業務管理方案
20140724 中小企業 QNAP Virtualization Station 快速導入業務管理方案20140724 中小企業 QNAP Virtualization Station 快速導入業務管理方案
20140724 中小企業 QNAP Virtualization Station 快速導入業務管理方案Amigo 陳兆祥
 
FAQ about Mozilla Space Taiwan
FAQ about Mozilla Space TaiwanFAQ about Mozilla Space Taiwan
FAQ about Mozilla Space TaiwanAmigo 陳兆祥
 
[201] salesforce for power user day 2
[201] salesforce for power user   day 2[201] salesforce for power user   day 2
[201] salesforce for power user day 2Amigo 陳兆祥
 
[201] salesforce for power user day 1
[201] salesforce for power user   day 1[201] salesforce for power user   day 1
[201] salesforce for power user day 1Amigo 陳兆祥
 
[201] salesforce for power user day 3
[201] salesforce for power user   day 3[201] salesforce for power user   day 3
[201] salesforce for power user day 3Amigo 陳兆祥
 

Plus de Amigo 陳兆祥 (14)

20140920 創業前要作的事
20140920 創業前要作的事20140920 創業前要作的事
20140920 創業前要作的事
 
以Code igniter為基礎的網頁前端程式設計
以Code igniter為基礎的網頁前端程式設計以Code igniter為基礎的網頁前端程式設計
以Code igniter為基礎的網頁前端程式設計
 
PHP CodeIgniter 框架之美
PHP CodeIgniter 框架之美PHP CodeIgniter 框架之美
PHP CodeIgniter 框架之美
 
20140824 如何協助業務部門達成業績目標與更精準的預測
20140824 如何協助業務部門達成業績目標與更精準的預測20140824 如何協助業務部門達成業績目標與更精準的預測
20140824 如何協助業務部門達成業績目標與更精準的預測
 
20140824 從離職到開始 crm 顧問的轉變
20140824 從離職到開始 crm 顧問的轉變20140824 從離職到開始 crm 顧問的轉變
20140824 從離職到開始 crm 顧問的轉變
 
20140824 認識與應用商業模式
20140824 認識與應用商業模式20140824 認識與應用商業模式
20140824 認識與應用商業模式
 
20140816 工程師要如何準備一場成功的簡報!
20140816 工程師要如何準備一場成功的簡報!20140816 工程師要如何準備一場成功的簡報!
20140816 工程師要如何準備一場成功的簡報!
 
20140809 如何加速行銷部門作業流程與編列預算
20140809 如何加速行銷部門作業流程與編列預算20140809 如何加速行銷部門作業流程與編列預算
20140809 如何加速行銷部門作業流程與編列預算
 
High Availability and High Performance Server Side
High Availability and High Performance Server SideHigh Availability and High Performance Server Side
High Availability and High Performance Server Side
 
20140724 中小企業 QNAP Virtualization Station 快速導入業務管理方案
20140724 中小企業 QNAP Virtualization Station 快速導入業務管理方案20140724 中小企業 QNAP Virtualization Station 快速導入業務管理方案
20140724 中小企業 QNAP Virtualization Station 快速導入業務管理方案
 
FAQ about Mozilla Space Taiwan
FAQ about Mozilla Space TaiwanFAQ about Mozilla Space Taiwan
FAQ about Mozilla Space Taiwan
 
[201] salesforce for power user day 2
[201] salesforce for power user   day 2[201] salesforce for power user   day 2
[201] salesforce for power user day 2
 
[201] salesforce for power user day 1
[201] salesforce for power user   day 1[201] salesforce for power user   day 1
[201] salesforce for power user day 1
 
[201] salesforce for power user day 3
[201] salesforce for power user   day 3[201] salesforce for power user   day 3
[201] salesforce for power user day 3
 

RESTful API Design

  • 1. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato RESTful API DesignRESTful API Design Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato
  • 2. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 特別感謝 ● 感謝 Mozilla 借出場地 ● 感謝陳兆祥先生幫助活動統籌
  • 3. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 大綱 ● 個人簡述 ● 為什麼要重視 API 設計 ● 比較傳統與 API 網頁設計 ● RESTful API 設計
  • 4. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 大綱 ● 個人簡述 ● 為什麼要重視 API 設計 ● 比較傳統與 API 網頁設計 ● RESTful API 設計
  • 5. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 個人簡述 ● 豐富的火星系統救火經驗 ● 喜歡資料庫 ● 喜歡貓 ● 出沒於 Hong Kong Linux User Group @ FB
  • 6. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 大綱 ● 個人簡述 ● 為什麼要重視 API 設計 ● 比較傳統與 API 網頁設計 ● RESTful API 設計
  • 7. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 為什麼要重視 API 設計 好的 API 設計, 不能讓你考試一百分,升職加薪
  • 8. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 但是可以讓你減少爆肝機會 (前題:老闆在你提升工作效率後不再追加工作)
  • 9. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 大綱 ● 個人簡述 ● 為什麼要重視 API 設計 ● 比較傳統與 API 網頁設計 ● RESTful API 設計
  • 10. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 誰需要重視 API 設計 等一下,我是網頁工程師 RESTful API 和我有關係嗎?
  • 11. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 傳統網頁流程 Client Server 1. 用戶發出 http://www.abc.com 的 Request 2. 伺服器根據準備 Data 和 Presention logic Presentation Code 4. 伺服器把 html 丟回用戶 Data 3. 伺服器把 Data 和 Presentation 結合成完整的 html Result html
  • 12. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 可怕的程式碼與數據交錯 ● Data 和 Presentation 混合, Presentation 無法單 獨 cache ,只要 Data 變動就必須重新產生 ● 無法徹底分割 Presentation 、 Business Logic 、 和 Data ,影響開發、測試、除錯的協同作業 ● 伺服器負責將 Data 和 Presentation 整合(簡稱 Data Binding ),消耗伺服器的 CPU 資源
  • 13. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato API 網頁工程師的看法 Client Server 1. 用戶發出 http://www.abc.com 的 Request 2. 伺服器回傳 Presentation 文件與 Scripting 檔案 Presentation Code Script Code 3. 用戶端瀏覽器執行 Scripting ,根據指示對 api.opensource.hk 作出 request 4. 伺服器以 json / xml 的格式回傳 Data Data 5. 瀏覽器把 html 和 Data 結合,然後在畫面顯示出來
  • 14. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 優點 1 :客戶端快取節省流量 表面上看起來,原先僅需一次 request 增加為兩次, 似乎花了更多的時間與網路流量! 但是,只要負責美工的同事不改變網頁外表。第一個 request 伺服器會回答 HTTP 304 Not Modified ,直 譯就是:回家吃自己~ Presentation 最近沒改動,用 之前的版本吧! 因為網頁的 Presentation 不用每次重傳,可以節省不 少網路流量(=省下錢$)
  • 15. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 優點 2 :資料與介面分離 現在 Presentation 和 Data 已經徹底分離! 開發和測試 Presentation 的 data mocking 可以使用 專門的 mock API 伺服器。 只要準備好 API 與測試資料,前端工程師就能專心工 作。前端延誤和後端工程師無關,不必背黑鍋~ 可再將執行架構改為 Presentation 在 Apache , API 在 Tomcat 。
  • 16. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 優點 3 :節省伺服器計算資源 可以不在伺服器做的東西,便不要放在伺服器 Data Binding 現在是交給瀏覽器處理,不再是伺服器 的工作,省下伺服器的 CPU 計算資源 ! 即使未來要支持 IOS , Android ,只要背後邏輯不 變,這些 API 將能全部重覆使用,節省開發時間!
  • 17. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 優點4:能重用的伺服器程式 即使未來要支持 IOS , Android ,只要背後邏 輯不變,這些 API 將能全部重覆使用,節省開 發時間
  • 18. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 大綱 ● 個人簡述 ● 為什麼要重視 API 設計 ● 比較傳統與 API 網頁設計 ● RESTful API 設計
  • 19. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 先談 RESTful 謬誤 server side 需要 stateless 正解: RESTful 只要求 Application Server 是 stateless , Server Side 其他部份可以 stateful
  • 20. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 要新一代支援 RESTful 的 noSQL 資料庫 正解: RESTful 和資料庫沒直接關係,你可以使用 PostgreSQL 、 MySQL 、或 Oracle
  • 21. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 一定需要用上 HTTP 的 GET, PUT, POST, DELETE 正解:統一介面 (Uniform interface) 只建議善用 HTTP ,使用其他技術實作的統一介面也能滿足 RESTful 要求
  • 22. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 使用 RESTful 的工程師都找不到女朋友 正解:(這倒有可能是事實)
  • 23. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato RESTful 的要求 ● Client-server (客戶端和伺服器結構) ● Cacheable (能夠利用快取機制增進性能) ● Layered system (分層式系統) ● Stateless protocol (通訊協定具有無狀態性) ● Uniform interface (統一介面) From Wiki
  • 24. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato RESTful 的要求 ● Client-server (客戶端和伺服器結構) ● Cacheable (能夠利用快取機制增進性能) ● Layered system (分層式系統) ● Stateless protocol (通訊協定具有無狀態性) ● Uniform interface (統一介面) From Wiki
  • 25. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 客戶端和伺服器結構 ● 滿足 RESTful 的系統必需存在客戶端和伺服器端 ● RESTful 只規範伺服器,和客戶端與伺服器端之 間的通訊協定
  • 26. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato RESTful 的要求 ● Client-server (客戶端和伺服器結構) ● Cacheable (能夠利用快取機制增進性能) ● Layered system (分層式系統) ● Stateless protocol (通訊協定具有無狀態性) ● Uniform interface (統一介面) From Wiki
  • 27. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 能夠利用快取機制增進性能 ● 系統內的所有東西都必須定義能否使用快取 ● 客戶端可以為首次可快取資源建立本地快取!在 下次 Request 時,客戶會把本地快取版本告訴伺 服器。如果伺服器發現資源沒有改動,便會要求 客戶端使用本地快取的資源。 ● 可以省下伺服器 CPU 資源和網路流量(=省錢) ● 不常變動的物件適合設定為可快取,如網頁界面 ● 詳見: HTTP conditional GET
  • 28. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato RESTful 的要求 ● Client-server (客戶端和伺服器結構) ● Cacheable (能夠利用快取機制增進性能) ● Layered system (分層式系統) ● Stateless protocol (通訊協定具有無狀態性) ● Uniform interface (統一介面) From Wiki
  • 29. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 分層式系統
  • 30. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato RESTful 的要求 ● Client-server (客戶端和伺服器結構) ● Cacheable (能夠利用快取機制增進性能) ● Layered system (分層式系統) ● Stateless protocol (通訊協定具有無狀態性) ● Uniform interface (統一介面) From Wiki
  • 31. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 以下內容非常重要,直接影響到閣下未來爆肝度 睡著了的朋友請起來聽講 (謎之聲:睡了的朋友又怎能看到這段文字?)
  • 32. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 淺談網路的不穩定性 ● 隨時會斷線!往往看起來正常,其實已經斷線 ● 使用 API 時,連線可能在信號送達伺服器前斷線 ● 也可能在伺服器正要傳回 API 結果時斷線 ● 更可能客戶端以為斷線,卻早已成功傳送資訊 ● 除非使用同一個 TCP/IP 連線,否則當客戶端先 發出 API1 ,然後再發出 API2 後,在次序錯亂的 情況下,伺服器有可能先收到 API2 ~
  • 33. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 無狀態通訊協定 1. 通訊協定具有無狀態性 2. atomic (原子) 3. 足夠完整的資料 4. 重新呼叫
  • 34. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 無狀態通訊協定 1. 通訊協定具有無狀態性 2. atomic (原子) 3. 足夠完整的資料 4. 重新呼叫
  • 35. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 通訊協定具有無狀態性 RESTful 伺服器端是被允許有狀態的 Application Server 必須是無狀態 RESTful 准許把狀態儲存到資料庫中,例如將登入狀 態的短期資訊放到短期資料庫 (Redis) 最簡單的程式說法: RESTful 禁止使用 HttpSession(Java) , session_start(PHP)
  • 36. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 無狀態通訊協定範例 1. 用戶發出 http://api.abc.com/user/60321?access- key=rbo9PUDgx3Bvl5Ij20fYEWct_CfH 2. Application Server 對 access-key 作出解密,得 到 Session ID=0x1A6C9C77869EF675 3. Application Server 根據 Session ID ,到 Redis 資料庫拿回登入狀態,知道用戶正是 User 60321 本人,並且有足夠權限使用這個 API 4. Application Server 到 PostgreSQL 資料庫拿資料 5. Application Server 把資料以 JSON 格式傳回用戶
  • 37. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 無狀態通訊協定 1. 通訊協定具有無狀態性 2. atomic (原子性) 3. 足夠完整的資料 4. 重新呼叫
  • 38. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato atomic (原子性) 每一個動作都必需是 atomic 。一個完整執行後的 API 呼叫不能讓伺服器端數據停留在不一致的狀態。 Each action call should be atomic. Any Successful API call should not leave server side in inconsistent state. 另一個說法:你不能使用二個(或以上) API 呼叫去 完成一個「動作」
  • 39. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 不符合 atomic 的範例 ● 你現在是光明破壞神三的工程師,因為遊戲內有 檢錢這個動作,所以有檢錢的 API /user/60321/single_user_coin_change (POST) POST_DATA = { "change_amount": 100, "description" : " 從怪物 645389890 的屍體上檢錢 ", "create_time" : "2014-07-05T16:35:46" }
  • 40. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato ● 現在主管突然覺得數字網太好賺,想連那部份也 自己來賺,要求讓遊戲中的金幣支援轉帳服務 ● 主管說:不用新建 API 啦,把現有的 single_user_coin_change 沿用,把「用戶A轉帳 到用戶B」這個動作拆成「從用戶A扣錢」和 「把錢加到用戶B」二個動作。 看到不符合的地方嗎?
  • 41. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato ● 後果是:新的轉帳功能推出後,有用戶發現轉帳 時金幣不翼而飛! ● 因為用戶完成「從用戶A扣錢」後,遇上藍畫面 或是網絡問題,沒法完成「把錢加到用戶B」動 作。
  • 42. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 前端工程師想出了解決方案:轉帳前先把這記錄存放 在客戶端硬碟 ● 程式重新啟動時發現未完成的轉帳記錄時,客戶 端需要: ● 先問伺候器,轉帳過程是停在那一步驟 ● 從當掉的步驟重來 不過對於硬碟故障的客戶,這方案沒用!
  • 43. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 後端工程師想出了另一個解決方案:藉 POST_DATA 中的 description 作配對。 ● 找出所有扣了A的錢而沒有為B加錢的轉帳,然 後作出數據回復 ● 需要定期掃瞄資料庫中的所有記錄,引起嚴重效 能問題 掃瞄程式超級難寫,後端工程師肝病可能性大升
  • 44. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 符合 atomic 的範例 ● 建立新的 API RESTful API /user/{user_id}/coin_transfer_transaction (POST) POST_DATA = { "from_user_id": "60321", "to_user_id": "89072", "amount": 100, "description" : " 從用戶 60321 轉帳到用戶 89072" "create_time" : "2014-07-05T16:35:46" } 當用戶當機或網路斷線,再重新執行一次 API 即可!
  • 45. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 無狀態通訊協定 1. 通訊協定具有無狀態性 2. atomic (原子) 3. 足夠完整的資料 4. 重新呼叫
  • 46. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 足夠完整的資料 每個 API 呼叫時都需要向伺服器提供足夠完整的資料 Each API call should provide sufficient information for server side to process.
  • 47. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 常見錯誤 ● 你不應該假設伺服器知道「現在狀態」 錯誤例子:玩中國象棋時,單純把用戶端指令用「炮 二平五」來回傳給伺服器
  • 48. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 不完整的資料範例 1. 在紅方第 31 步行動時,紅方發出「炮二平五」指令 2. 這時網絡某個路由器發生嚴重錯亂,把「炮二平五」的網 絡封包送到火星 3. 紅方電腦等 10 秒後沒有收到伺服器回應,以為網絡錯 誤,於是再發出「炮二平五」指令,這個封包經由正常的 路由器,所以 1 秒內就被傳送到伺服器 4. 10 分鐘後,送往火星的錯誤封包終於被送到伺服器 5. 這時已經到達第 55 步紅方行動,剛好紅方有炮棋在二 線,伺服器沒法知道這是第 31 步時的封包,並且以為這 是第 55 步的指令,因此執行「炮二平五」的指令,並且 拒絕之後用戶真正第 55 步的指令
  • 49. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato ● RESTful 的「足夠資料」,在中國象棋中最簡單 實現的方法便是把每隻棋子的位置以及棋局的最 後更改時間,在「炮二平五」的指令中同時傳給 伺服器。 ● 這樣伺服器便有足夠資料去分辨第 31 步時路經火 星的封包。(因為棋局狀況和最後更改時間不符 合)
  • 50. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato ● 不過,每次都把完整狀態丟來丟去是白痴,因為 這將會大量消耗網絡封包 ● 如果這是梭哈遊戲,你有機會可以攔截封包,事 先得知對手蓋牌,有資安疑慮! 所以:基於網路效能和資安考量, API 所用的資料可 以放在伺服器, API 只需說明正在引用那份資料。
  • 51. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 完整的資料範例 /chinese_chess_game/{game_id} (PUT) PUT_DATA = { "step_id" : 31 "action" : " 炮二平五 " } 伺服器收到這個 Request 時,會從短期資料庫中拿 出第 31 步的棋局。 如果第 31 步已經被執行,伺服器會檢查已經存在的 第 31 步是否等於 " 炮二平五 " 。如果是,傳回"成 功"給客戶端;如果不是,則傳回錯誤。
  • 52. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 無狀態通訊協定 1. 通訊協定具有無狀態性 2. atomic (原子) 3. 足夠完整的資料 4. 重新呼叫
  • 53. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 重新呼叫 ● 在客戶端,任何未成功收到傳回訊息的 API ,只 需要重新呼叫。 ● 伺服器端需要懂得處理重覆 API request ● 在建立新物件時,把客戶端時間也放到 API request 中,讓伺服器能分辦是否收到重覆的 HTTP POST
  • 54. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato RESTful 的要求 ● Client-server (客戶端和伺服器結構) ● Cacheable (能夠利用快取機制增進性能) ● Layered system (分層式系統) ● Stateless protocol (通訊協定具有無狀態性) ● Uniform interface (統一介面) From Wiki
  • 55. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 統一介面 ● 所有介面都應該基於物件,而不是行動 ● 前述的遊戲檢錢,就是建立 single_user_coin_change 這個物件 ● 一個物件正常有4種行動:查詢,更改,誕生, 刪除 ● 查詢:一般使用 HTTP GET method ● 更改:一般使用 HTTP PUT method ● 誕生:一般使用 HTTP POST method ● 刪除:一般使用 HTTP DELETE method
  • 56. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 統一介面範例 /v3/user/1234/book/54389 ● v3 = 使用第三版本的 /user/1234/book/54389 API ● user/1234/book/54389 = 這是關於使用者 1234 屬下的書 本 54389 – GET = 取得書本內容 – PUT = 更改書本內容 – DELETE = 刪除書本紀錄 /v3/user/1234/book/ ● GET = 取得使用者 1234 屬下的書本 ● POST = 在使用者 1234 屬下建立新的書本
  • 57. ©©Triton Ho @ Mar's PotatoTriton Ho @ Mar's Potato 問題時間