在Web系統中,Ajax技術已經成爲提升用戶體驗的必備技術。開發Ajax程序,涉及兩方面的內容:一是客戶端技術,二是服務器端技術。 javascript
(1)客戶端技術 html
核心工做是經過JavaScript向服務器發送數據和接收數據。初次以外還涉及兩個工做,一是數據的展現,所以涉及Html DOM、CSS等相關技術;二是數據處理,所以涉及JSON、XML等數據格式處理技術。在實際開發過程當中,能夠藉助一些客戶端框架,來提升工做效率。 java
(2)服務器端技術 jquery
核心工做是完成在服務器端接收和發送數據。 ajax
在動做方法中處理Ajax請求,重點關注的是如何向客戶端返回數據。 服務器
對於接收數據,因爲Ajax客戶端程序還是經過Get或Post方式發送數據,所以處理方式和接收非Ajax請求一致。 框架
向服務器端發送數據,通常有以下幾種形式。 ide
對於向客戶端返回結構單一的數據,可使用純文本格式,如刪除操做是否成功的提示,用法如示例1所示。 函數
示例1 post
public ActionResult Delete(int? id) { //省略代碼 if(manager.Delete(id)) { return Content("1"); //操做成功 } return Content("0"); } |
對於示例1,客戶端接收的數據是"0"或"1",根據數據客戶端可作出刪除操做是否成功的提示。
對於局部刷新的效果,多數狀況是向服務器端請求一個局部的頁面,示例2展現了針對Ajax請求返回一個分部視圖。
示例2
/// 獲取當前用戶的分組信息 public ActionResult ListGroups() { User user = Session["CurrentUser"] as User; if (user == null) { return this.Content("<script>window.location='" + Url.Action("Login", "Account") + "'</script>"); } int userId = user.UserId; //分組列表數據 var groups = context.PrivateGroups.Where(a => a.OwnerId == userId).ToList(); //返回分部視圖 return PartialView("GroupList"); } |
注意使用PartialView()方法返回分部視圖。
若是向客戶端返回複雜結構的數據,通常須要由服務器端向客戶端返回客戶端支持的數據格式,如JSON格式和XML格式。在不一樣的服務器端平臺中,都有相應的API 支持將對象轉化成這些格式的數據。如示例3所示。
示例3
/// 獲取當前用戶分組信息 public ActionResult ListGroupsToJson() { User user = Session["CurrentUser"] as User; if (user == null) return Content(""); int userId = user.UserId; //分組列表數據 var groups = (from g in context.PrivateGroups where g.OwnerId == userId select g ).ToList(); return Json(groups,JsonRequestBehavior.AllowGet); } |
示例3中, Json()方法負責將對象序列化爲JSON數據,其中第一個參數是要序列化的對象,第二個 JsonRequestBehavior 類型的參數,是一個枚舉類型,包含AllowGet 和 DenyGet 兩個值,分別表明容許Get 請求和不容許 Get 請求。
客戶端獲取JSON數據後,通常須要對JSON數據進行處理,以某種形式展現出來。多數狀況會使用客戶端控件來處理,好比 BootStrapTables 。
在使用ASP.NET MVC 提供的 Json()方法返回JSON數據時,對待DateTime類型的數據處理每每不能知足咱們的要求。在實際開發中咱們一般會使用 以下方法:
Newtonsoft.Json.JsonConvert.SerializeObject(object value)
示例3中的最後一行代碼能夠換作以下:
return Content( JsonConvert.SerializeObject(groups) );
總的來講,在Ajax程序開發中,客戶端的編碼工做是必不可少的,可是若是使用ASP.NET MVC 框架,這些編碼工做就會大大減小,甚至在一些簡單的應用場景,不須要手工編寫JavaScript 代碼。
ASP.NET MVC 的這種功能是由 AjaxHelper 類型的對象提供的,此類和 HtmlHelper 是對應的,也是輔助視圖輸出的,特殊的是它用於生成具備Ajax功能的視圖。相應地,在視圖基類 WebViewPage 中包含名稱爲 AjaxHelper 類型的對象 Ajax ,經過Ajax 對象調用相應的方法實現Ajax 功能視圖的輸出。
最多見的一種場景是表單提交,在客戶端使用jQuery 時,通常會藉助於 $.ajax() 和 $.post() 提交表單。其中,大部分的編碼工做是從表單中獲取提交的數據,工做量每每隨着表單的字段增長而增長。
在ASP.NET MVC 中,藉助於 Ajax 對象提供的 BeginForm()方法,便可完成此功能。以下語法展現了BeginForm() 一個典型的重載版本定義。
public static MvcForm BeginForm(
this AjaxHelper ajaxHelper,
string actionName,
object routeValues,
AjaxOptions ajaxOptions
)
和 HtmlHelper 中的BeginForm() 不一樣的是,多了AjaxOption 類型的參數,經過該類對請求發送先後進行相關的設置,主要屬性如表10-1 所示。
表10-1 AjaxOptions 類的主要屬性
主要屬性 |
說 明 |
string UpdateTargetId |
服務器響應來更新的 DOM 元素的 ID |
string Confirm |
提交請求以前顯示在確認窗口中的消息 |
string HttpMethod |
HTTP 請求方法("Get"或"Post") |
InsertionMode InsertionMode |
將響應插入目標 DOM 元素的模式,默認爲Replace |
int LoadingElementDuration |
控制在顯示或隱藏加載元素時的動畫持續時間(毫秒) |
string OnBegin |
在更新頁面以前調用的 JavaScript 函數 |
string OnSuccess |
在成功更新頁面以後調用的 JavaScript 函數 |
string OnComplete |
在實例化相應數據後但在更新頁面前調用的JavaScript函數 |
string OnFailure |
在頁面更新失敗時調用的JavaScript 函數 |
string Url |
向服務器發送請求的 |
示例4展現了 Ajax.BeginForm()的使用方法。
示例4
@section scripts{ <script type="text/javascript" src="@Url.Content("~/Scripts/jquery.unobtrusive-ajax.min.js")"> </script> } @using (Ajax.BeginForm("AddRecord", new AjaxOptions { UpdateTargetId = "AddRecordMessage" })) { <textarea name="Content" cols="" rows="" class="importArea"> 在想什麼呢?記下來吧</textarea> <p> <input type="submit" value="發 表 "/ class="button"> <a id="AddRecordMessage" class="message"></a></p> } //動做方法-添加記錄 [HttpPost] public ActionResult AddRecord(string Content) { if (ModelState.IsVaild) { Record record= new Record(); record.Content=Content; db.Records.Add(record); if (db.SaveChanges()>0) { return Content("記錄保存成功!"); } Else { return Content("記錄保存失敗!"); } } else { return Content("請按要求填寫信息!"); } } |
在示例4中,只用到 AjaxOption 類型的一個參數 UpdateTargetId ,其值爲<a>標籤的Id屬性,<a>標籤用於顯示Ajax 方式提交後,從服務器端返回的消息提示。
須要注意使用ASP.NET MVC 提供的 Ajax 功能,須要引入 jquery.unobtrusive-ajax.min.js 腳本,該文件提供非侵入方式提供 Ajax 功能,而不生成Html 和 JavaScript 混合的代碼,這和驗證框架處理方式是一致的。示例4中 Ajax.BeginForm() 方法生成的Html 代碼以下。
<form action="/Home/AddRecord"
data-ajax="true" data-ajax-mode="replace"
data-ajax-update="#AddRecordMessage"
id="form0" method="post">
<!--省略代碼-->
</form>
對於一些簡單的應用場景,使用 Ajax.BeignForm()方法基本不須要手工編寫任何 JavaScript 腳本,但對一些特殊需求,仍是須要編寫 JavaScripts 函數實現,這些函數能夠經過 AjaxOptions 的屬性賦值進行調用。示例5 展現了 AjaxOptions 的 OnSucess 屬性和 Confirm 屬性的用法。
示例5
<script type="text/javascript"> function addRecordSuccess(data) { $("#AddRecordMessage").html(data).show().hide(5000); } </script> @using (Ajax.BeginForm("AddRecord", new AjaxOptions { OnSuccess = "addRecordSuccess", Confirm="確認要提交麼?" })) { <textarea name="Content" cols="" rows="" class="importArea"> 在想什麼呢?記下來吧 </textarea> <p> <input type="submit" value="發 表 "/ class="button"> <a id="AddRecordMessage" class="message"></a> </p> } |
在示例5代碼中,OnSucess 屬性設置爲 JavaScript 函數 addRecordsSuccess(), 使用函數實現消息顯示後在5秒內自動隱藏。另外,使用 Confirm 彈出提交前的確認提示框。
除了表單提交外,還有一個典型的應用場景,當點擊一個連接時,在同一個頁面局部加載頁面內容。對於這種場景,Ajax對象提供了兩種生成Ajax連接的方法,即 Ajax.ActionLink() 和 Ajax.RouteLink() ,和Html對象的兩個對應的方法相比,多了一個AjaxOption參數。如示例6所示。
示例6
<ul class="friendCatalog" id="groupItems"> @foreach (Friends.Models.PrivateGroup m in ViewBag.Groups) { <li> @Ajax.ActionLink(m.GroupName,"ListFriends","Friend", new{groupId=m.GroupId}, new AjaxOptions(){OnSuccess="loadFriendsByGroup"}) <img src="@Url.Content("~/images/edit.gif")" /> <img src="@Url.Content("~/images/delete.gif")" /><span> @m.FriendRelations.Count()</span> </li> } <!--省略部分代碼--> </ul> |
示例6運行後,Ajax.ActionLink()對應生成的Html代碼以下所示。
<a data-ajax="true" data-ajax-success="loadFriendsByGroup"
href="/Friend/ListFriends?groupId=4">連接內容</a>