李琨
到目前為止,傳統(tǒng)的Java Web MVC框架(Struts、WebWork、SpringMVC、etc.)還無(wú)法很好地支持REST風(fēng)格的架構(gòu)設(shè)計(jì)。它們?cè)谠O(shè)計(jì)之初時(shí)基本上都是圍繞著基于HTML表單的交互模式來(lái)設(shè)計(jì)的,View的粒度難以達(dá)到單個(gè)頁(yè)面以下。不能把響應(yīng)Ajax請(qǐng)求而返回的XML/JSON/純文本格式的數(shù)據(jù)簡(jiǎn)單地認(rèn)為是WebMVC框架中的View,實(shí)際上這個(gè)時(shí)候這些數(shù)據(jù)的語(yǔ)義已經(jīng)與傳統(tǒng)的Web MVC架構(gòu)中的View的語(yǔ)義相距甚遠(yuǎn)。
傳統(tǒng)的WebMVC框架一個(gè)最大的問(wèn)題是它們看待URL的方式與REST有很大的差別。REST把服務(wù)器端所有的URL都當(dāng)作是抽象的資源(相當(dāng)于是面向?qū)ο笤O(shè)計(jì)中的接口),雖然WebMVC也強(qiáng)調(diào)不應(yīng)該將硬編碼的URL(例如:http://www.xxx.com/yyy/zzz/abcd.jsp)直接暴露出來(lái),而應(yīng)該通過(guò)某個(gè)Controller來(lái)暴露,將這個(gè)頁(yè)面配置為Controller的一個(gè)View,但是WebMVC框架并沒(méi)有有意識(shí)地將URL當(dāng)作抽象的資源來(lái)看待和設(shè)計(jì)。
還有一個(gè)較為嚴(yán)重的問(wèn)題是傳統(tǒng)的Web MVC框架基本上都只支持GET和POST兩種HTTP方法,而不支持PUT和DELETE方法,而Servlet API是支持上述所有的HTTP方法的(支持doPut和doDelete方法)。
舉個(gè)例子,SpringMVC所支持的HTTP方法封裝在org.springframework.web.servlet.supportWebContentGenerator類(lèi)中,其中只有METHOD_HEAD、METHOD_GET、METHOD_POST幾個(gè)常量,而沒(méi)有METHOD_PUT、METHOD_DELETE,顯然其作者并不認(rèn)為有必要支持HTTP的PUT和DELETE方法。
我沒(méi)有考察過(guò)Struts和WebWork,估計(jì)結(jié)果應(yīng)該是一樣的,而且也沒(méi)有聽(tīng)說(shuō)過(guò)Strust和WebWork的作者有支持REST風(fēng)格架構(gòu)設(shè)計(jì)的計(jì)劃。JSF呢?雖然GavinKing以前在某地說(shuō)過(guò)JSF完全可以支持REST,上次見(jiàn)面我沒(méi)有仔細(xì)向他請(qǐng)教這個(gè)問(wèn)題,但是可以肯定的是JSF從來(lái)就沒(méi)有把支持REST風(fēng)格的架構(gòu)設(shè)計(jì)作為他們的核心目標(biāo)之一。
所以在這個(gè)方面,Java社區(qū)要比Ruby社區(qū)落后很多了。目前只能脫離開(kāi)傳統(tǒng)的Web MVC框架,基于ServletAPI來(lái)建造一個(gè)符合REST要求的新的服務(wù)器端架構(gòu)(當(dāng)然,SpringIoC、Hibernate等框架仍然可以保留)。好在不需要我們親自來(lái)做這個(gè)事情,已經(jīng)有一些Java的服務(wù)器端框架可以支持REST了。例如:Restlet(http://www.restlet.org)。另外還有一些橫跨瀏覽器和服務(wù)器的設(shè)計(jì)模式可以利用,詳情見(jiàn)《Ajax模式與最佳實(shí)踐》。
聯(lián)系客服