4/18/2007

REST 簡介

前言

寫這篇是因為我在 滿紙荒唐言,一把心酸淚 裡面有講到
我連REST 的好處都不甚了解,就大張旗鼓的吹 REST 的好?
所以我開始努力 survey REST 的東西,終於在 OSDC 主講 T
he furture of RoR - The new features in RoR 2.0。原本以為自己已經徹底瞭解 REST,但是隨著時間的逼近,我越來越發現「我不知道 REST 真正的好處」。最後,當我在 OSDC 講完之後,大家就七嘴八舌給我一些意見,越討論越發現我真是個笨蛋
在 OSDC 這種場合,我才是學生,場下聽的強者們才是我的老師
現在的我,有了大家的加持後,反而越來越有自信了點,我終於允許我在 Blog 寫有關於 REST 的文章。

REST is about Resource

在講 REST 之前,我們來看看Resource 。當你了解 Resource,那麼你就了解了 REST。我們來看看 Wikipedia 這張圖,這個三角形是在講解 Resource 最重要的三個東西,Nouns,Verb,Type。

Nouns

在網路上,每個URL帶給我們的意義其實就是代表各式各樣的資源(Resource),有些可能代表你的個人日誌,有些代表我出去玩的圖片,有些代表你最喜歡的歌手的音樂,有些代表你朋友搞笑的影片。Resource 裡面,Nouns 其實是一個 URL,他代表網路上面 Resource 的唯一的位址,同一個 resource 理論上來說,應該只有一個 URL 代表這個 Resource。用超過一個 URL 來代表同一個 Resource 是不夠漂亮的方式。

Type

而 Type 是什麼呢?我們剛剛講 URL 代表Resource 的位址。但是 Resource 其實跟大家想的有點不太一樣,resource 不是只代表一個檔案,他是代表一個概念。舉個例子,這張圖片
是 一張PNG圖片,裡面是我的 Email 。他的位置是在 http://www.thegiive.net-a.googlepages.com/image.png,但是如果我今天將這個 PNG 轉檔成為 JPG,他的位置就變成了 http://www.thegiive.net-a.googlepages.com/image.jpg。雖然兩者的 URL 不相同,但是對我們來說,PNG 跟 JPG 這兩張圖其實代表的意義是相同的,裡面的圖案就是我的 Email。

所以,儘管 Format 不同,他們依舊是同一個 Resource,而這些 Format 就是 Type

好, 這些東西大家應該都可以了解吧。我們問些奇怪的問題,假設今天有一個 XML file http://www.thegiive.net- a.googlepages.com/image.xml 這個XML檔案裡面記載著我的 Email 帳號
<xml>
<email>thegiive at gmail dot com</email>
</xml>
那麼這個 XML File 跟上面的圖,算是同一個 Resource 嗎?是的,雖然 XML 跟 JPG ,PNG 是完全不同的東西,但是他們都記載同樣的意義,那個意義就是我的 Email 帳號,也就是他們代表同一個 resource。

如果你能夠接受不同格式的檔案其實代表同一個 Resource 的想法,那麼今天這個網址
http://abc.com/blog/1
如 果以 HTML Format 來說,他可能是一個可以顯示在 Browser 上面的 HTML ,裡面記載這個 Blog 的內容。但是如果是 XML Format,他可能是一個記載這個 Blog 作者是誰的XML 。如果是以 RSS Format 來看,他可能是這個 Blog 的最新文章。但是儘管 Format 不同,內容不同,但是他們還是代表同一個 resource ,也就是這個 Blog。

在 Web 上面,Resource 是一個概念,而不僅僅是一個檔案。一個 resource 可能有各種不同的 Content Type,但是依舊代表同一個 resource。

Verbs

至於三角形的最後一角Verbs ,就是操作 Resource 的方式。我們該如何操作網路上各式各樣的資源呢?

Web 用宏觀來說,其實就是一個超級大的資料庫,裡面有各式各樣不同的 resource,每個 URL 都是指向各種不同的 Resource,我們每天上網,其實都是藉由 HTTP 來 request 各式各樣不同的 Resource。

既然 Web 根本就是一個網路上面 Resource 的資料庫,每個 Resource 都是跟資料庫裡面的 Data Entry 類似。那麼有用過資料庫的人都知道,我們每天對資料庫的每個 Data Entry 做四個動作,也就是經典的 CRUD(Create,Read,Update,Delete)。盡管 SQL 指令再多,其實我們對資料庫的操作,都超不出 CRUD 這四個動作。

那們,我們對 Web 上面的 resource,有沒有相對應的 CRUD 呢?

RFC 2616 裡面講到, HTTP 1.1 一共有八個 method(我在演講中提到只有四個 Method,是錯誤的,謝謝聽眾指正。),裡面有兩個 Method 是大家不可能不懂的
  • GET
  • POST
雖然 HTTP 定義八個 Method之多,但是大家在 Coding Web 時只使用這兩個 Method。
原因很簡單,因為最多人使用的 HTTP Client,也就是 Browser,只支援 GET 和 POST。所以,我們之前的 Coding,都是只用 GET 和 POST 來對 Web Resource 來做 CRUD。
CREATE:POST http://abc.com/users/create/
READ:GET http://abc.com/user/show/1
UPDATE:POST http://abc.com/user/update/1
DELETE:GET http://abc.com/user/delete/1
我們必須用部份的 URL 來表示我們對這個 Resource 的操作,這樣做也沒什麼不好,但是要知道 URL 其實是要來指定 Resource 位置的,URL 不是拿來表示 Verbs 的。而且這樣做等於我們使用四個 URL 來表示同一個 Resource,這跟一個 Resource 理論上來說只能有一個 URL 牴觸。

RFC 定義的 HTTP 1.1 裡面,其實有四個 Method 是直接 Mapping 到 CRUD 的,那就是 GET,POST,PUT,DELETE。既然已經 HTTP 1.1 已經有對應好的 Method,那為什麼我們要捨近求遠,硬是要使用 GET POST 來設計出 CRUD,為什麼不用原本就規定好的 Mapping 來做 CRUD 呢?

沒錯,這就是 REST。讓大家不需要再捨近求遠,不需要用非 Web Standard 的方式來做 Web Development。

REST 的詳細定義就請看 Wikipedia上面的介紹, 本人就不詳細敘述了。在定義上來說,REST 並不等於 HTTP,REST 是一種 Architectural Style,而非一種 Standard,所以 REST 並沒有 toolkit ,也沒有 W3C Spec。相對起來,HTTP 才是一種 Standard ,有相對應的 toolkit,W3C Spec。HTTP 是一種 REST 的實做,也是最成功的實做。但是我們以實用為主,並不是那麼在乎太過細部的差別,所以以後我不會太強調 REST 跟 HTTP 兩者意義上的區分。

4 則留言:

Unknown 提到...

感謝啦,把REST寫得很精簡,看得懂。 能讓人看得懂就是好!

bkuo 提到...

thanks for your introduction!

fishjerky 提到...

我也一直無法明確的解釋REST
看了上面的例子總算是懂了
感謝 \^o^/

匿名 提到...

深入淺出!,我好像有那麼一點懂了....