首先,要分為.net 2.0和.net 3.5這兩種情況來考慮
一:.net 2.0情況下
ajax可以調用 aspx.cs 里面加了 [webmethod]的靜態方法,而不能調用 asmx 里面加了[webmethod]的方法或者是靜態方法
調用aspx.cs里面的webmethod方法的時候,還必須在web.config里面添加如下代碼
<httpModules> <add name="ScriptModule" type="System.Web.Handlers.ScriptModule, System.Web.Extensions, Version=3.5.0.0,
Culture=neutral, PublicKeyToken=31BF3856AD364E35"/> </httpModules>
二:在.net 3.5的情況下
前台ajax可以調用aspx.cs 里面加了[webmethod]的靜態方法(不需要自己手動添加web.config的配置)
也可以調用 asmx里面加了[webmethod]的方法(不能寫靜態,寫靜態就調用不到了)
需要在asmx里面 去掉 [System.Web.Script.Services.ScriptService] 的注釋 (這也是為什么在.net 2.0里面不能用ajax調用 asmx 里面的 webmethod ,因為.net 2.0里面沒有 System.Web.Script.Services.ScriptService)
下面分別在.net 3.5 和 .net 2.0下面 使用webmethod 來試試
在.net 3.5的情況下
,使用System.Web.Script.Services.ScriptService 可以讀取 asmx 里面的 webmethod方法
如果你把asmx里面的方法,進行了static靜態化,那么在查看這個 pt.aspx頁面的時候,你會發現 webmethod的方法居然不見了。
鑒於上篇文章中提到的Json優點:易讀性、可擴展性和操作方便,接下來我們實現一個簡單的例子Demo,場景是:查詢商品信息;實現過程:Web程序通過Jquery調用WebService,Web Service返回Json對象,成功調用后,對返回的JSon結果進行處理,下面我們看一下具體實現過程:
1、 web項目 如下圖:
跑起來如下,有2個功能,1個是顯示所有的產品,1個是查詢單一的產品,我們這里根據不同還設置了 get方式提交數據,以及post方式提交數據
2、 添加實體類Product.cs到工程中,並且序列化,代碼如下
[Serializable] public class Product { public long ProductId { get; set; }//產品ID public string ProductName { get; set; } public decimal Price { get; set; } public int Stock { get; set; }//產品儲存量 }
3、 添加數據類ProductData.cs類到工程中,此類主要完成數據的查詢操作,代碼如下所示:
using System; using System.Collections.Generic; using System.Web; using System.Linq; namespace web { public class ProductData { private List<Product> plist = new List<Product> { new Product(){ProductId=1,ProductName="筆記本", Price=10000, Stock=10}, new Product(){ProductId=2,ProductName="格子絨長袖襯衫", Price=90, Stock=20}, new Product(){ProductId=3,ProductName="純棉長袖T恤", Price=99, Stock=40}, new Product(){ProductId=4,ProductName="炫彩T恤", Price=67, Stock=30}, new Product(){ProductId=5,ProductName="直筒褲男牛仔褲", Price=100, Stock=20}, new Product(){ProductId=6,ProductName="[無印嚴選]純色V領長袖T恤", Price=67, Stock=50}, new Product(){ProductId=7,ProductName="英倫學院派馬夾", Price=44, Stock=40}, new Product(){ProductId=8,ProductName="純棉連帽寬松衛衣", Price=66, Stock=30}, new Product(){ProductId=9,ProductName="純棉多口袋工裝褲", Price=80, Stock=990}, new Product(){ProductId=10,ProductName="假兩件長袖T恤", Price=89, Stock=30}, }; /// <summary>返回所有的產品 /// /// </summary> /// <returns></returns> public List<Product> GetAllProduct() { return plist; } /// <summary>根據產品ID,返回一個產品 /// /// </summary> /// <param name="id"></param> /// <returns></returns> public Product GetByProductId(int id) { return plist.FirstOrDefault(p => p.ProductId == id); } /// <summary>根據價格,返回符合價格相同的產品列表 /// /// </summary> /// <param name="price"></param> /// <returns></returns> public List<Product> GetByPrice(decimal price) { return plist.Where(p => p.Price == price).ToList(); } } }
4、 添加ASP.NET Web Service 到工程中,命名為ProductServic.asmx,如下
Ø 引用命名空間:System.Web.Script.Services.ScriptService
Ø 給方法添加注解:[ScriptMethod(ResponseFormat = TheResponseFormat, UseHttpGet = true/false)]
ResponseFormat:方法要返回的類型,一般為Json或者XML
UseHttpGet:true表示 前台ajax只有“Get”方式可以訪問此方法
using System; using System.Collections.Generic; using System.Linq; using System.Web; using System.Web.Services; using System.Web.Script.Services; //如果想使用ScriptMethod,則必須引用此命名空間 namespace web { /// <summary> /// ProductService 的摘要說明 /// </summary> [WebService(Namespace = "http://tempuri.org/")] [WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)] [System.ComponentModel.ToolboxItem(false)] // 若要允許使用 ASP.NET AJAX 從腳本中調用此 Web 服務,請取消對下行的注釋。否則前台ajax無法調用到數據 [System.Web.Script.Services.ScriptService] //這句話就是,如果你想在前台想用jquery或者是其他的ajax來調用下面的帶有WebMethod的方法,
那么這個注釋就要去掉,問題是這個只有.net 3.5有,如果是.net 2.0呢?怎么解決? public class ProductService : System.Web.Services.WebService { private ProductData datasouuce //這里是一個屬性 { get { return new ProductData(); } } /// <summary>獲取所有的產品 /// /// </summary> /// <returns></returns> [WebMethod(Description = "獲取所有的產品")] [ScriptMethod(ResponseFormat = ResponseFormat.Json, UseHttpGet = true)] //ResponseFormat:方法要返回的類型,一般為Json或者XML //UseHttpGet:true表示前台的ajax是通過“Get”可以訪問此方法,如果前台ajax通過POST,則報錯 //false表示前台的ajax是通過"post"來訪問此方法,如果前台ajax通過get,則報錯 public List<Product> GetAllProduct() { return datasouuce.GetAllProduct(); } /// <summary>根據產品ID,返回一個產品 /// /// </summary> /// <param name="id"></param> /// <returns></returns> [WebMethod(Description = "根據產品ID,返回一個產品")] [ScriptMethod(ResponseFormat = ResponseFormat.Json, UseHttpGet = false)]//這里限制前台必須是post一個id過來,而不是get方式 public Product GetByProductId(string id) { return datasouuce.GetByProductId(Convert.ToInt32(id)); } /// <summary>根據價格,返回符合價格相同的產品列表 /// /// </summary> /// <param name="price"></param> /// <returns></returns> [WebMethod(Description="根據價格,返回符合價格相同的產品列表")] [ScriptMethod(ResponseFormat = ResponseFormat.Json, UseHttpGet = true)] public List<Product> GetByPrice(decimal price) { return datasouuce.GetByPrice(price); } } }
5、 在Defualt.aspx頁面引用Jquery類庫
引用Google網絡jquery 類庫http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.js
或者本地類庫<script src="Scripts/jquery-1.4.1.js" type="text/javascript"></script>
6、 在Defualt.aspx頁添加如下HTML代碼:
<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="Default.aspx.cs" Inherits="web._Default" %> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head runat="server"> <title></title> <script src="Scripts/jquery-1.4.1.js" type="text/javascript"></script> <script type="text/javascript"> $(document).ready(function () { }) function showAll() { $.ajax({ type: "GET", //當前台ajax用get方式的時候,后台asmx頁面的方法的UseHttpGet 必須為 true contentType: "application/json; charset=utf-8", url: "ProductService.asmx/GetAllProduct", dataType: "json", success: insertCallback, error: errorCallback }); } function showOne() { var idNumber = $("#txtId").val(); $.ajax({ type: "POST", //當前台ajax用post方式的時候,后台asmx頁面的方法的UseHttpGet 必須為 false data: "{id:" + idNumber + ",tt:" + new Date().getTime() + "}", //這里傳值和asmx的方法一樣的參數列表(或者是多余asmx的參數列表),
例如后台是id,這里也必須是id,但是我這里還是多傳了一個值tt,代表刷新時間,防止ajax有緩存(后面才知道,這是浪費,因為post本來就是不緩存數據,只有get才緩存) contentType: "application/json; charset=utf-8", url: "ProductService.asmx/GetByProductId", dataType: "json", success: insertCallback, error: errorCallback }); } function insertCallback(result) { $('#productList > thead').empty(); $('#productList > tbody').empty(); //json返回來的數據默認就是 d if (result["d"] == null) {//如果result["d"] 為 null ,則表示沒有查詢到想對應的值 alert("沒有數據"); return; } //清空原來的數據 $('#productList > thead:last').append('<tr><td>產品名稱</td><td>價格</td><td>庫存</td></tr>'); if (result["d"] != null && result["d"].length == undefined) { //既不是空,但是長度又是未定義,就表示只有1個值 $('#productList > tbody:last').append('<tr><td>' + result["d"].ProductName + '</td><td>' + result["d"].Price +
'</td><td>' + result["d"].Stock + '</td></tr>'); } else { for (var i = 0; i < result["d"].length; i++) { var product = eval(result["d"][i]); $('#productList > tbody:last').append('<tr><td>' + product.ProductName + '</td><td>' + product.Price + '</td><td>' + product.Stock + '</td></tr>'); } } } function errorCallback(XMLHttpRequest, textStatus, errorThrown) { $('#productList > thead').empty(); $('#productList > tbody').empty(); alert(errorThrown + ':' + textStatus); } </script> </head> <body> <form id="form1" runat="server"> <div id="listContainer" class="container"> <div id="title"> <br /> <input id="btnAll" type="button" value="通過get方式顯示所有的產品" onclick="showAll()" /><br /> <br /> <br> 請輸入要搜索的產品ID :<input type="text" id="txtId"> <input id="btnOne" type="button" value="通過post方式顯示1個產品" onclick="showOne()" /> </div> <table id="productList"> <thead> </thead> <tbody> </tbody> </table> </div> </form> </body> </html>
$.ajax方法有以下屬性:
Type: HTTP請求方法,在做查詢操作時,經常用Get方法
contentType:在請求頭部的類型,由於Web Service返回Json對象,此處值為:application/json; charset=utf-8
dataType:定義返回的類型
Success:調用成功時,要執行的方法
error:調用失敗是,要執行的方法
9、 執行程序,效果如下:
至此,使用 jquery 查詢webService返回的 Json 對象已經完成
在.net 2.0 的情況下
1、無參數的方法調用, 注意:1.方法一定要靜態方法,而且要有[WebMethod]的聲明
后台<C#>:
using System.Web.Script.Services; [WebMethod] public static string SayHello() { return "Hello Ajax!"; }
前台<JQuery>:
$(function() { $("#btnOK").click(function() { $.ajax({ //要用post方式 type: "Post", //方法所在頁面和方法名 url: "data.aspx/SayHello", contentType: "application/json; charset=utf-8", dataType: "json", success: function(data) { //返回的數據用data.d獲取內容 alert(data.d); }, error: function(err) { alert(err); } }); //禁用按鈕的提交 return false; }); });
2、帶參數的方法調用
后台<C#>:
using System.Web.Script.Services; [WebMethod] public static string GetStr(string str, string str2) { return str + str2; }
前台<Jquery代碼>:
$(function() { $("#btnOK").click(function() { $.ajax({ type: "Post", url: "data.aspx/GetStr", //方法傳參的寫法一定要對,str為形參的名字,str2為第二個形參的名字 data: "{'str':'我是','str2':'XXX'}", contentType: "application/json; charset=utf-8", dataType: "json", success: function(data) { //返回的數據用data.d獲取內容 alert(data.d); }, error: function(err) { alert(err); } }); //禁用按鈕的提交 return false; }); });
3:返回數組方法的調用
后台<C#>:
using System.Web.Script.Services; [WebMethod] public static List<string> GetArray() { List<string> li = new List<string>(); for (int i = 0; i < 10; i++) li.Add(i + ""); return li; }
前台<Jquery代碼>:
/// <reference path="jquery-1.4.2-vsdoc.js"/> $(function() { $("#btnOK").click(function() { $.ajax({ type: "Post", url: "data.aspx/GetArray", contentType: "application/json; charset=utf-8", dataType: "json", success: function(data) { //插入前先清空ul $("#list").html(""); //遞歸獲取數據 $(data.d).each(function() { //插入結果到li里面 $("#list").append("<li>" + this + "</li>"); }); alert(data.d); }, error: function(err) { alert(err); } }); //禁用按鈕的提交 return false; }); });
4: