熱點推薦:
您现在的位置: 電腦知識網 >> 編程 >> .NET編程 >> 正文

事實證明Ajax的世界更需要ASP.NET MVC

2013-11-13 10:31:12  來源: .NET編程 

  真正走進ASPNET MVC的世界才知道它的精彩

  拋棄WebServiceNET中用 jQuery 調用 WCF——原來拋棄WebService之後還可以用jQuery調用ASPNET MVC的Controller

  Ajax為主的應用不需要ASPNET MVC原來Ajax的世界更需要ASPNET MVC

  曾經天真的想法在實踐中證明了它的天真但在從天真到事實的過程中得到的是成長

  下面就談談我是如何認識到這個的相比於結論其中的過程更重要

  還是以之前文章中的博客園站內短消息功能(顯示當前用戶短消息列表)為例開始用的是jQuery插件Templates進行列表數據綁定後來遇到了兩個問題

  ) 在綁定時需要根據條件判斷生成不同的元素比如用戶發過來的短消息發件人顯示為鏈接如果是系統通知則顯示為文本Templates對這樣的操作處理起來不是很方便

  ) 綁定後的數據無法在服務端重用有時從搜索引擎友好或者用戶體驗的角度在頁面第一次加載時不用ajax在頁面加載後點擊刷新或分頁鏈接時才使用ajax這樣就要在服務端與客戶端分別維護數據綁定操作

  也就是說原來服務端返回的是實體類對象列表現在要返回的是將數據與Html組裝起來的字符串

   開始我們考慮的是一種丑陋的方法用StringBuilder進行字符串拼接生成數據綁定結果服務器端WCF服務中的代碼如下

  

  顯然這種方法易出錯維護性差

   接著我們考慮了第二種方法(參考自Render User Control as String Template)通過Web User Control生成字符串WCF服務中的代碼如下


  Page page = new Page();
Control control = pageLoadControl(~/Controls/MsgListControlascx);
((IRenderable<List<SiteMsg>>)control)PopulateData(siteMsgList);
StringBuilder sb = new StringBuilder();
using (StringWriter sw = new StringWriter(sb))
{
using (HtmlTextWriter htw = new HtmlTextWriter(sw))
{
controlRenderControl(htw);
return sbToString();
}
}

  由於MsgListControlascx的類型是動態編譯生成的所以無法通過強制類型轉換將control轉換為MsgListControl類型然後傳遞數據給它

  這裡需要通過一個另外的IRenderable<T>接口來實現數據的綁定MsgListControl實現了這個接口代碼如下


  public partial class MsgListControl : UserControl IRenderable<List<SiteMsg>>
{
public void PopulateData(List<SiteMsg> siteMsgList)
{
rptMsgListDataSource = siteMsgList;
rptMsgListDataBind();
}
}

public interface IRenderable<T>
{
void PopulateData(T data);
}

  在WCF服務中通過調用接口中的PopulateData方法進行數據的綁定

  這個方法增加了額外的接口顯得有些復雜

   後來我們想到了ASPNET MVC雖然不熟悉但要嘗試一下看能否更好地解決這個問題

  於是上ASPNET MVC 用Razor咱們也MVC一把

  應用場景在現有的VS Web Site項目中應用ASPNET MVC MsgController收到請求後由Inbox(一個Action)將包含短消息列表的整個頁面視圖返回給客戶端當用戶點擊頁面的刷新或者分頁鏈接時通過Ajax發起POST請求以獲取短消息列表MsgController收到請求後由List(一個Action)將短消息列表的視圖返回給客戶端

  期望的效果短消息列表視圖能重用Inbox與List使用的是同一個視圖

  一開始遇到了兩個小問題

  a) MapRoute配置之後訪問出現HTTP Error Not Found錯誤原因是訪問的網址沒有文件名未走ASPNET管線解決方法是在nfig的systemwebServer中加上以下的配置


  <validation validateIntegratedModeConfiguration=false />
<modules runAllManagedModulesForAllRequests=true /> 

  b) 繼續訪問出現The resource cannot be found錯誤解決方法由於用的是Web Site項目要將Controllers文件夾移至App_Code

  然後進入MVC相關代碼編寫先從Ajax調用部分開始

  Controller的代碼如下


  public class MsgController : Controller
{
[HttpPost]
public ActionResult List(SiteMsgQuery msgQuery)
{
List<SiteMsg> siteMsgList = GetInboxMsgList(msgQuery);
return View(MsgList siteMsgList);
}
}

  需要注意的就一個地方[HttpPost]既然是Ajax調用當然要響應POST請求

  View的代碼(MsgListcshtml)如下


  @using CNBlogsUcHomeExternalServiceMsgWcfService
@model List<SiteMsg>
@foreach(SiteMsg msg in Model){
<div class=msg_item>
<div class=msg_sender>@msgSenderName</div>
<div class=msg_title><a /msg/item/@msgid/>@msgSubject</a></div>
<div class=msg_sendtime>@msgSendTimeToString(yyyyMMdd HH:mm)</div>
</div>
}

  比在ascx中寫起來方便多了

  客戶端js調用代碼如下


  function GetMsgList(pageIndex pageSize) {
var msgQuery = {}
msgQueryPageIndex = pageIndex;
msgQueryPageSize = pageSize;
$ajaxSettingsdataType = plain/text;//不要用json
$ajaxSettingsurl = /msg/list;
$ajaxSettingsdata = {msgQuery: + JSONstringify(msgQuery) + };
$ajaxSettingssuccess = function (data) {
$(#msg_listl(data);
};
$ajax();
}

  需要注意的是兩個地方(因為服務器端Controller返回的不是json格式的數據)

  a) dataType不要用json用jQuery默認的就行如果指定的話就用plain/text

  b) 返回數據就在data中不要通過datad獲取

  這樣用ASPNET MVC就輕松搞定Ajax調用比之前的WCF StringBuider ascx都要方便

  原來在ASPNET MVC中使用Ajax如此方便完全可以取代以前用的WCF中轉站

  解決了Ajax的問題接著處理整個頁面的顯示

  在頁面的View中直接重用剛才Ajax所用的View就行了示例代碼如下

  View(Inboxcshtml)


  <!DOCTYPE html>
<html>
<head>
<title></title>
</head>
<body>
@HtmlPartial(MsgList)
</body>
</html>

  Control


  public class MsgController : Controller
{
public ActionResult Inbox()
{
SiteMsgQuery msgQuery = new SiteMsgQuery()
{
PageIndex =
PageSize =
};
List<SiteMsg> siteMsgList = GetInboxMsgList(msgQuery);
return View(Inbox siteMsgList);
}
}

  搞定!真的很方便!想要的解決方案就是它ASPNET MVC!


From:http://tw.wingwit.com/Article/program/net/201311/13877.html
  • 上一篇文章:

  • 下一篇文章:
  • 推薦文章
    Copyright © 2005-2013 電腦知識網 Computer Knowledge   All rights reserved.