<a href="#%E7%9B%AE%E5%BD%95">目錄</a>
<a href="#%E5%89%8D%E6%96%87%E5%88%97%E8%A1%A8">前文清單</a>
<a href="#%E6%89%A9%E5%B1%95%E9%98%85%E8%AF%BB">擴充閱讀</a>
<a href="#restful-api">RESTful API</a>
<a href="#rest-%E5%8E%9F%E5%88%99">REST 原則</a>
<a href="#%E6%97%A0%E7%8A%B6%E6%80%81%E5%8E%9F%E5%88%99">無狀态原則</a>
<a href="#%E9%9D%A2%E5%90%91%E8%B5%84%E6%BA%90">面向資源</a>
<a href="#restful-api-%E7%9A%84%E4%BC%98%E5%8A%BF">RESTful API 的優勢</a>
<a href="#rest-%E7%BA%A6%E6%9D%9F">REST 限制</a>
<a href="http://blog.csdn.net/jmilk/article/details/53150084">用 Flask 來寫個輕部落格 (1) — 建立項目</a>
<a href="http://blog.csdn.net/jmilk/article/details/53152158">用 Flask 來寫個輕部落格 (2) — Hello World!</a>
<a href="http://blog.csdn.net/jmilk/article/details/53153382">用 Flask 來寫個輕部落格 (3) — (M)VC_連接配接 MySQL 和 SQLAlchemy</a>
<a href="http://blog.csdn.net/jmilk/article/details/53184903">用 Flask 來寫個輕部落格 (4) — (M)VC_建立資料模型和表</a>
<a href="http://blog.csdn.net/jmilk/article/details/53187575">用 Flask 來寫個輕部落格 (5) — (M)VC_SQLAlchemy 的 CRUD 詳解</a>
<a href="http://blog.csdn.net/jmilk/article/details/53229180">用 Flask 來寫個輕部落格 (6) — (M)VC_models 的關系(one to many)</a>
<a href="http://blog.csdn.net/jmilk/article/details/53239740">用 Flask 來寫個輕部落格 (7) — (M)VC_models 的關系(many to many)</a>
<a href="http://blog.csdn.net/jmilk/article/details/53241361">用 Flask 來寫個輕部落格 (8) — (M)VC_Alembic 管理資料庫結構的更新和降級</a>
<a href="http://blog.csdn.net/jmilk/article/details/53264049">用 Flask 來寫個輕部落格 (9) — M(V)C_Jinja 文法基礎快速概覽</a>
<a href="http://blog.csdn.net/jmilk/article/details/53292248">用 Flask 來寫個輕部落格 (10) — M(V)C_Jinja 常用過濾器與 Flask 特殊變量及方法</a>
<a href="http://blog.csdn.net/jmilk/article/details/53303870">用 Flask 來寫個輕部落格 (11) — M(V)C_建立視圖函數</a>
<a href="http://blog.csdn.net/jmilk/article/details/53306560">用 Flask 來寫個輕部落格 (12) — M(V)C_編寫和繼承 Jinja 模闆</a>
<a href="http://blog.csdn.net/jmilk/article/details/53321939">用 Flask 來寫個輕部落格 (13) — M(V)C_WTForms 服務端表單檢驗</a>
<a href="http://blog.csdn.net/jmilk/article/details/53327164">用 Flask 來寫個輕部落格 (14) — M(V)C_實作項目首頁的模闆</a>
<a href="http://blog.csdn.net/jmilk/article/details/53332204">用 Flask 來寫個輕部落格 (15) — M(V)C_實作博文頁面評論表單</a>
<a href="http://blog.csdn.net/jmilk/article/details/53342517">用 Flask 來寫個輕部落格 (16) — MV(C)_Flask Blueprint 藍圖</a>
<a href="http://blog.csdn.net/jmilk/article/details/53352359">用 Flask 來寫個輕部落格 (17) — MV(C)_應用藍圖來重構項目</a>
<a href="http://blog.csdn.net/jmilk/article/details/53363109">用 Flask 來寫個輕部落格 (18) — 使用工廠模式來生成應用對象</a>
<a href="http://blog.csdn.net/jmilk/article/details/53365714">用 Flask 來寫個輕部落格 (19) — 以 Bcrypt 密文存儲賬戶資訊與實作使用者登陸表單</a>
<a href="http://blog.csdn.net/jmilk/article/details/53368626">用 Flask 來寫個輕部落格 (20) — 實作系統資料庫單與應用 reCAPTCHA 來實作驗證碼</a>
<a href="http://blog.csdn.net/jmilk/article/details/53385381">用 Flask 來寫個輕部落格 (21) — 結合 reCAPTCHA 驗證碼實作使用者注冊與登入</a>
<a href="http://blog.csdn.net/jmilk/article/details/53445271">用 Flask 來寫個輕部落格 (22) — 實作部落格文章的添加和編輯頁面</a>
<a href="http://blog.csdn.net/jmilk/article/details/53448906">用 Flask 來寫個輕部落格 (23) — 應用 OAuth 來實作 Facebook 第三方登入</a>
<a href="http://blog.csdn.net/jmilk/article/details/53539710">用 Flask 來寫個輕部落格 (24) — 使用 Flask-Login 來保護應用安全</a>
<a href="http://blog.csdn.net/jmilk/article/details/53542686">用 Flask 來寫個輕部落格 (25) — 使用 Flask-Principal 實作角色權限功能</a>
<a href="http://blog.csdn.net/jmilk/article/details/53677411">用 Flask 來寫個輕部落格 (26) — 使用 Flask-Celery-Helper 實作異步任務</a>
<a href="http://blog.csdn.net/jmilk/article/details/53741676">用 Flask 來寫個輕部落格 (27) — 使用 Flask-Cache 實作網頁緩存加速</a>
<a href="http://blog.csdn.net/Jmilk/article/details/53782360">用 Flask 來寫個輕部落格 (29) — 使用 Flask-Admin 實作背景管理 SQLAlchemy</a>
<a href="http://blog.csdn.net/jmilk/article/details/53782865">用 Flask 來寫個輕部落格 (30) — 使用 Flask-Admin 增強文章管理功能</a>
<a href="http://blog.csdn.net/jmilk/article/details/53970235">用 Flask 來寫個輕部落格 (31) — 使用 Flask-Admin 實作 FileSystem 管理</a>
<a href="http://www.cnblogs.com/shiyangxt/archive/2008/10/07/1305506.html">cookie 和 session 的差別詳解</a>
REST(Representational State Transfer):是一種軟體架構的設計風格,而不是一種标準。主要用于 C/S 架構的軟體設計,也能很好的支援 B/S 架構,為軟體設計提供了一組原則和限制條件,但這些原則和限制的條件均不具有标準性。是以 REST 可以了解為是一組沒有嚴格标準的架構限制條件和設計原則。而滿足 REST 風格的應用或設計,就是 RESTful.
API: 為外部提供了可以通路應用程式内容資料資源和業務資源的接口, 并且這個接口應該是統一的, 不依賴于硬體平台/軟體作業系統/程式設計語言的.
REST 具有通過 HTTP/HTTPS(無狀态傳輸協定) 直接傳輸資料(XML/JSON)的特性, 是以 C/S 或 B/S 之間的互動請求是無狀态的. 相對的, 在 <<用 Flask 來寫個輕部落格>> 系列博文中 Flask-Login 的實作, 其需要通過 session(Server) 和 cookie(Browser/client) 結合來實作在伺服器端或用戶端中儲存使用者的身份和登入狀态, 以此來實作不同的使用者在不同的頁面中可以具有不同通路權限的效果. REST 會使用另外的方式來這個目的, 例如 Openstack 中的 Keystone 認證中間件.
資源以 URI(統一資源辨別符) 的形式向外部公開, 以 URL(統一資源定位器) 的形式來通路擷取. 大概而言, 伺服器端 Application 的所有概念都可以定義為一種資源. 使用 URL/URI 能夠更好的契合 HTTP/HTTPS 協定, 結合 HTTP/HTTP 協定的内置 Methods(GET/POST/PUT/DELETE) 可能非常友善的實作對資源的 CRUD 資料操作, 除此之外還能夠自定義出不同的 action 方法并将其綁定到不同的 URL 中來擴充請求的類型, 實作了不僅限于資源的業務邏輯操作. EG. Openstack Nova 中的資源 server, 其含有的 ../os-start, ../os-stop 等 URL, 對應了 啟動/關閉 虛拟機的業務操作. 總的來說, 每個資源都使用唯一的 URI 辨別, 而資源的 URL 就是 HTTP 方法調用的目标.
URI: <code>protocol://hostname[:port]/path</code> 定義了某一類資源
URL: <code>protocol://hostname[:port]/path/[;parameters][?query]#fragment</code> 定義了某一個具體的資源機關
是以 URL 一般都了解為 URI 的子集.
基于狀态與基于無狀态 service 在分布式系統中的差別與了解:
(因水準問題, 并不嚴謹, 僅為當下的了解, 歡迎指正)
前者, 用戶端的 Cookie 中儲存了 session_id, 如果在伺服器中該 session_id 對應的 Session 仍然存在的話将會由該 Session 來繼續維護使用者請求的狀态等公共資訊. 但問題是, 如果在這個過程中該伺服器當機的話, 則需要重新在另外一台伺服器中建立一個 Session 并與用戶端建立再次連接配接并生成 Cookie, 顯然在分布式系統中這個過程是比較無謂. 這就是基于狀态的 Web service 的分布式系統的弊端, 所有的伺服器都需要維護使用者請求狀态. 在這個前提下, 提出了類似于 LDAP(使用者資訊集中管理伺服器) 這樣的狀态集中管理機制, 由單獨的一台或一類伺服器或服務來為整個分布式系統提供身份鑒權功能子產品. 那麼其先決條件當然就是, 所有的使用者請求都必須是無狀态的, 不再有所有的伺服器都維護着使用者請求狀态等公共資訊的情況發生. 而且還需要引入别的實作方式來滿足這一方面的需求, 在 Openstack 中就引入了 Keystone 身份認證服務. 這樣做的好處還在于改善了分布式系統的可靠性以及可伸縮性.
是以 RESTful API 的優勢在于:
解耦了用戶端和伺服器
高可靠
易擴充
不依賴與平台和語言
簡單輕量
注意: 這裡的限制是針對這次的 blog 項目所設計的, 并部一定完全設用于所有應用場景, 需要結合實際進行改進, 是以不應滿足與使用, 而是要在不斷的實踐中加深對 REST 的了解和累積經驗.
用戶端和服務端關心的業務是完全分離的, 前者不能處理資料的持久化, 後者不能處理與使用者頁面表現層相關的邏輯. 在 blog application 中, 整個項目都會作為服務端.
服務端是無狀态的, 請求與響應的過程中服務端不會保留任何的 session 等狀态資訊. 處理請求所需要的資訊都會被存儲在用戶端中, 或者被每一次單獨的請求所攜帶. Flask Application 接受的每一個請求都可以攜帶儲存在用戶端中的 cookie 資料, 再交由服務端解析并以此判斷權限等資訊, 但不保留.
服務端公布的所有資源都必須保證統一的接口形似, 即 :
接口必須是基于資源的
不直接傳回資料庫中的資料而是包裝成為 JSON 或 XML 等形式後傳回
所有資源都應用一緻的包裝形式
服務端傳回的資料應該足夠完整能夠滿足用戶端的業務需求
允許中間層的存在, EG. 能夠支援使用 負載均衡/代理/緩存 等中間層服務
傳回正确的 HTTP/HTTPS 狀态碼