jQuery调用WCF需要注意的一些问题
昨天,博客園首頁增加了Digg功能。在該功能中我們開始嘗試使用jQuery直接調(diào)用WCF。之前我們采用的方案是jQuery調(diào)用Web Service,然后WebService再調(diào)用服務(wù)層。這樣調(diào)用主要是因為之前需要調(diào)用不同域名下的WCF服務(wù),因為跨域調(diào)用的問題,就要通過Web Service中轉(zhuǎn)一下。而這次Digg功能調(diào)用的是同一個應(yīng)用程序下的WCF,用jQuery直接調(diào)用WCF是更好的選擇。在嘗試這種方式的過程中遇到的一些問題和一些需要注意的地方需要記錄一下,所以就寫了這篇隨筆。
xland的jQuery調(diào)WCF給了我們很大幫助,在這里感謝xland!在探索技術(shù)的過程中,將自己解決問題的經(jīng)驗記錄下來,不僅可以備忘、總結(jié),而且可以幫助遇到同樣問題的朋友,這也是寫博客的一種樂趣吧。
進入正題,jQuery調(diào)用WCF需要注意的一些問題:
1. WCF的配置(WCF服務(wù)宿主于IIS 7)
1)WCF服務(wù)相關(guān)配置:
在需要調(diào)用的接口方法(OperationContract)上加上屬性[WebInvoke(RequestFormat = WebMessageFormat.Json, ResponseFormat = WebMessageFormat.Json, BodyStyle = WebMessageBodyStyle.WrappedRequest)],比如:
[ServiceContract]?publicinterfaceIDiggService????{??????
??????? [OperationContract][WebInvoke(RequestFormat?=WebMessageFormat.Json,?ResponseFormat?=WebMessageFormat.Json,?BodyStyle?=WebMessageBodyStyle.WrappedRequest)]stringGetDiggCountList(stringentryIdList);
????}
給服務(wù)實現(xiàn)類加上屬性:
[AspNetCompatibilityRequirements(RequirementsMode?=AspNetCompatibilityRequirementsMode.Allowed)]publicclassDiggService?:?IDiggService????{
?????}
否則調(diào)用時會出現(xiàn)錯誤:“IIS 7.0 Detailed Error - 500.0 - System.ServiceModel.ServiceActivationException”。
2) Web.config中的WCF相關(guān)配置:
? 需要注意兩個地方的配置:
a)? binding="webHttpBinding",開始設(shè)置為binding="basicHttpBinding",出現(xiàn)錯誤提示:
The endpoint at 'DiggService.svc' does not have a Binding with the None MessageVersion.? 'System.ServiceModel.Description.WebScriptEnablingBehavior' is only intended for use with WebHttpBinding or similar bindings.
b)? <enableWebScript/> ,啟用這個設(shè)置才能讓W(xué)CF支持Ajax調(diào)用,否則調(diào)用時WCF會返回這樣的錯誤:
二、客戶端jQuery調(diào)用注意
開始按照調(diào)用Web Servcie的方式調(diào)用:
$.ajax({????????url:?'/wcf/DiggService.svc/GetDiggCountList',
????????data:?'{"entryIdList":"'+entryIdList?+'"}',
????????type:?'post',
????????dataType:?'json',contentType:?'application/json;?charset=utf8',
????????success:?function(data)?{if(data.d)?{}
????????????}
????????},
????????error:?function(xhr)?{
????????????alert(xhr.responseText);
????????}
????});
在FireFox中能成功調(diào)用,但在IE 8和Google Chrome中,調(diào)用后返回的卻是IIS 7的錯誤信息:IIS 7.0 Detailed Error - 400.0 - Bad Request。
后來將 contentType: 'application/json; charset=utf8' 改為 contentType: 'text/json'問題就解決了。
jQuery調(diào)用Web Service與WCF還有一個不同之處在參數(shù)格式的處理上:
比如上面代碼中的data: '{"entryIdList":"' + entryIdList + '"}',如果將參數(shù)名的雙引號去掉,即data: '{entryIdList:"' + entryIdList + '"}',可以正常調(diào)用Web Service,調(diào)用WCF會出現(xiàn)Json反序列化的異常。
三、其他需要注意的地方
如果WCF服務(wù)所在的IIS站點中綁定了多個域名, 在沒有設(shè)置baseAddressPrefixFilters的情況下,會出現(xiàn)錯誤提示:
This collection already contains an address with scheme http.? There can be at most one address per scheme in this collection.Parameter name: item
設(shè)置好baseAddressPrefixFilters,比如:
這樣在訪問http://www.cnblogs.com時能正常調(diào)用,但訪問http://cnblogs.com時調(diào)用就出錯(IIS 7.0 Detailed Error - 404.0 - Not Found),因為之前的代碼中使用的是相對地址調(diào)用,實際調(diào)用的是http://cnblogs.com/wcf/DiggService.svc/GetDiggCountList,由于設(shè)置了baseAddressPrefixFilters,不允許這樣調(diào)用,只能改為絕對地址(http://www.cnblogs.com/wcf/DiggService.svc/GetDiggCountList),這樣又會造成跨域調(diào)用。這個問題目前還不知如何解決。
四、遺留問題
如何控制緩存,比如:如何在WCF返回時設(shè)置Expires Header和If-Modified-Since,避免頻繁的WCF調(diào)用。
五、總結(jié)
jQuery調(diào)用WCF的要點:
1. [WebInvoke(RequestFormat = WebMessageFormat.Json, ResponseFormat = WebMessageFormat.Json, BodyStyle = WebMessageBodyStyle.WrappedRequest)]
2. [AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
3.? binding="webHttpBinding"
4. <enableWebScript/>?
5.? contentType: 'text/json'
(轉(zhuǎn) dudu)
總結(jié)
以上是生活随笔為你收集整理的jQuery调用WCF需要注意的一些问题的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 如何打开滚筒洗衣机的门锁?
- 下一篇: 如何编写解决方案?