JavaScript基于XMLHttpRequest的Ajax请求

 

      在web应用中,前台和后台通信交互是必不可少的,如:js获取后台数据库信息、用户在前端发送控制指令等等,这些都需要通信交互。

      一般的方式是:后台暴露一个接口,然后前端对该接口发送请求,并附带相关参数。后台暴露的接口统称为web service,其中按协议分为:SOAP 和REST的。从统一性和标准性来说,基于REST的服务接口无疑是当今的主流。

      前端获取后台信息的方式也有很多种,如:asp/jsp前后台代码混合的方式;使用<script>、<iframe>标签请求后台信息;以及现在大规模的ajax方式。ajax方式对于一般web应用开发者来说,可以借助于第三方ajax框架来完成,主流的ajax框架有:JQuery、Dojo、Ext等等,他们不但有丰富的UI效果,封装了浏览器之间的差异,而且在使用ajax上也是十分简洁。

      在有些情况,我们希望了解ajax框架这些异步请求的内部是如何做到的,而XmlHttpRequest正是ajax的核心。 

 

       以下说明都是基于XmlHttpRequest的ajax方式。

       第一段代码演示的功能有:

      1、XmlHttpRequest中如何同步和异步ajax请求?

      2、如何请求Soap协议的服务?

      3、如何传递不同的数据结构给服务的(分:xml/json)?

      4、asp.net封装的ScriptManager是怎么实现ajax的?

        

       

Ajax方式 XmlHttpRequest/ScriptManger
  1 <%@ Page Language="C#" AutoEventWireup="true" CodeFile="commAjax.aspx.cs" Inherits="commAjax" %>
  2 
  3 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
  4 <html xmlns="http://www.w3.org/1999/xhtml">
  5 <head id="Head1" runat="server">
  6     <title></title>
  7     <script type="text/javascript">
  8         function commAjaxClick() {
  9             var XHR = getXMLHttpRequest();
 10             var _format = "json"; //"xml";//
 11             //回调函数是否同步。如这个XHR为同步的话,的等XHR回调方法执行完毕后,再执行DClientService的相关方法。调试可看效果。
 12             var _isAsynchro = false//true; // 
 13             //注意URL格式,DClientDemo为需要调用的方法。_isAsynchro为是否异步。如果为true的话同时进行。
 14             XHR.open("POST", "http://localhost/DClientService/DClientService.asmx/DClientDemo", _isAsynchro); //http post 需要加 /DClientDemo
 15             if (_format == "xml") {
 16                 XHR.setRequestHeader("Content-Type", "application/x-www-form-urlencoded;"); //http post : application/x-www-form-urlencoded;SOAP 1.1:text/xml; charset=utf-8
 17                 //XHR.setRequestHeader("SOAPAction", "http://tempuri.org/DClientDemo"); //SOAP 1.1需要设置
 18                 XHR.onreadystatechange = function () { httpReqCallback.apply(XHR); }; //XHR应用于回调函数中的this
 19                 XHR.send("req='wangsh'&_age=26&_salary=8600.5&_isWedding=true");
 20                 //post方式的参数格式:"req='wangsh'&_age=26&_salary=8600.5&_isWedding=true"
 21                 //get方式:send方法没有无法传递参数,可以在url携带参数,格式如:url+"?req='wangsh'&_age=26"
 22             }
 23             else if (_format == "json") {
 24                 //Content-Type设置为json格式,即数据以json进行交换,得到的结果也是json的
 25                 XHR.setRequestHeader("Content-Type", "application/json; charset=utf-8");
 26                 XHR.onreadystatechange = function () { httpReqCallback.apply(XHR); }; //XHR应用于回调函数中的this
 27                 var parObj = new Object();
 28                 parObj.req = 'wangsh';
 29                 parObj._age = 26;
 30                 parObj._salary = 8600.5;
 31                 parObj._isWedding = true;
 32                 XHR.send(Sys.Serialization.JavaScriptSerializer.serialize(parObj));
 33             }
 34 
 35             //以下为:使用的是经过ScriptManager封装后的ajax方法,直接像使用c#后台类那样,
 36             //需要在页面添加 <asp:ScriptManager>服务端控件
 37             DClientService.set_defaultSucceededCallback(webSrvCallback); //回调函数
 38             var _contentObj = new Object();                              //构造上下文对象
 39             _contentObj.name = "wangsh";
 40             DClientService.set_defaultUserContext(_contentObj);          //上下文
 41             DClientService.DClientDemo("wangsh", 26, 8000.08, false);    //调用webservice方法 
 42         }
 43         
 44         function httpReqCallback() {
 45             //每一个XMLHttpRequest对象AJAX过程中的readyState状态都会发生4次变化,每次变化都触发一个onreadystatechange事件,也就是调用四次该方法
 46             //具体状态值详解请参考:http://www.cn-cuckoo.com/2007/07/16/the-details-for-five-states-of-readystate-9.html
 47             if (this.readyState == 4) //请求状态为4表示成功
 48             {
 49                 if (this.status == 200) //http 状态200表示OK
 50                 {
 51                     alert(this.responseText);
 52                 }
 53                 else //http 返回状态失败
 54                 {
 55                     alert("服务端返回状态" + this.statusText);
 56                 }
 57             }
 58         }
 59 
 60         function webSrvCallback(result, userContext, methodName) {
 61             alert("1、操作结果: " + Sys.Serialization.JavaScriptSerializer.serialize(result) + "\n" +
 62             "2、上下文: " + Sys.Serialization.JavaScriptSerializer.serialize(userContext) + "\n" +
 63              "3、调用的web service方法名: " + methodName);
 64         }
 65 
 66         function getXMLHttpRequest() {
 67             //>=IE 7 和 firefox
 68             if (window.XMLHttpRequest) {
 69                 return new window.XMLHttpRequest();
 70             }
 71             else {
 72                 //Msxml2.XMLHTTP用在高版本的IE5/6,Microsoft.XMLHTTP用在《IE 5
 73                 var progIDs = ['MSXML2.XMLHTTP.5.0', 'MSXML2.XMLHTTP.4.0', 'MSXML2.XMLHTTP.3.0', 'MSXML2.XMLHTTP', 'Microsoft.XMLHTTP'];
 74 
 75                 for (var i = 0; i < progIDs.length; i++) {
 76                     try {
 77                         var xmlHttp = new ActiveXObject(progIDs[i]);
 78                         return xmlHttp;
 79                     }
 80                     catch (ex) { }
 81                 }
 82                 return null;
 83             }
 84         }
 85     </script>
 86 </head>
 87 <body>
 88     <div>
 89         <br />
 90         &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
 91         <input type="button" style="width: 150px" value="简单ajax 测试" onclick="javascript:commAjaxClick()" />
 92         <br />
 93         <br />
 94     </div>
 95     <form id="form1" runat="server">
 96     <asp:ScriptManager ID="ScriptManager1" runat="server">
 97         <Services>
 98             <asp:ServiceReference Path="http://localhost/DClientService/DClientService.asmx"
 99                 InlineScript="false" />
100         </Services>
101     </asp:ScriptManager>
102     </form>
103 </body>
104 </html>

 

   

 

      第二段代码演示的功能有:

      1、如何请求REST协议的服务?

      2、js如何跨域?<跨域请参考: ArcGIS for Server 10.1系列 - 动态获取权限Token >

 

 

      

ajax方式 以post请求REST服务
 1 function initToken() {
 2             var XHR = commClass.get_xmlHttpRequest();
 3             if (XHR != null) {
 4                 //POST方式请求Rest
 5                 XHR.open("POST", agsTokenUri, false);
 6                 XHR.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");
 7                 XHR.onreadystatechange = function () {
 8                     tokenCallback.apply(XHR);
 9                 };
10                 //IP方式
11                 XHR.send("username=wangsh&password=123456&client=referer&referer=" + appUri + "&expiration=1000&f=pjson");
12                 //HTTP Referer方式
13                 //XHR.send("username=wangsh&password=123456&client=referer&referer=" + appUri + "&expiration=1000&f=pjson");
14             }
15             XHR = null;
16         }
17 
18         /**
19         * 回调函数
20         */
21         function tokenCallback() {
22             try {
23                 if (this.readyState == 4) //请求状态为4表示成功
24                 {
25                     if (this.status == 200) //http 状态200表示OK
26                     {
27                         var _backInfo = eval('(' + this.responseText + ')');
28                         var _token = _backInfo.token;
29                         if (_token != null) {
30                             init(_token);
31                         }
32                     }
33                     else //http 返回状态失败
34                     {
35                         alert("服务端返回状态" + this.statusText);
36                     }
37                 }
38             }
39             catch (ex0) {
40             }
41         }

 

 

 

 

posted @ 2010-04-15 17:03  爱图--UpdooGIS  阅读(1494)  评论(0编辑  收藏  举报