如果获取的数据文件存放在远程服务器上(域名不同,也就是跨域获取数据),则需要使用jsonp类型。

使用这种类型的话,会创建一个查询字符串参数 callback=? ,这个参数会加在请求的URL后面。

服务器端应当在JSON数据前加上回调函数名,以便完成一个有效的JSONP请求。

如果要指定回调函数的参数名来取代默认的callback,可以通过设置$.ajax()的jsonp参数。

注意,JSONP是JSON格式的扩展。他要求一些服务器端的代码来检测并处理查询字符串参数。

 

如果指定了script或者jsonp类型,那么当从服务器接收到数据时,实际上是用了<script>标签而不是XMLHttpRequest对象。

这种情况下,$.ajax()不再返回一个XMLHttpRequest对象,并且也不会传递事件处理函数,比如beforeSend。

在一个jsonp请求中重写回调函数的名字。这个值用来替代在"callback=?"这种GET或POST请求中URL参数里的"callback"部分,比如{jsonp:'onJsonPLoad'}会导致将"onJsonPLoad=?"传给服务器。

 

JSONP的实现思路

  1. 前端创建script标记,设置src,添加到head中(你可以往body中添加)
  2. 后台返回一个js变量jsonp,这个jsonp就是请求后的JSON数据
  3. 回调完成后删除script标记(还有一些清理工作如避免部分浏览器内存泄露等)
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <title></title>
    <script src="js/jquery.min.js"></script>
    <script>
        function SaveData() {
            var UserName = "星辰雾海";
            $.ajax({
                type: "post",
                url: "http://116.228.89.136:8032/test.aspx",
                dataType: "jsonp",
                //这两句指定回调函数为:CallBackUser
                jsonp: 'callback',
                jsonpCallback: 'CallBackUser',
                data: { UserName: UserName },
                success: function (data) {
                    //jsonp请求,不会执行此函数,只执行CallBackUser
                    alert(data.UserName);
                }
            });
        }
        function CallBackUser(jsonData) {
            alert(jsonData.UserName);
        }
    </script>
</head>
<body>
    <input type="button" id="btnAdd" value="Test" onclick="SaveData()" />
</body>
</html>

请求Url:

http://116.228.89.136:8032/test.aspx?callback=CallBackUser&UserName=%E6%98%9F%E8%BE%B0%E9%9B%BE%E6%B5%B7&_=1457492166376

这个地址是自动拼接而成,注意中间拼接的 jsonp 参数的值,是你本地页面中的函数名称,在data属性中设置。

服务端代码:

protected void Page_Load(object sender, EventArgs e)
        {
            //http://116.228.89.136:8032/test.aspx?callback=jQuery11130304913979023695_1457491748431&jsonp=CallBackUser&UserName=%E6%98%9F%E8%BE%B0%E9%9B%BE%E6%B5%B7&_=1457491748433
            string json = "{UserName:\"My nam is "+Request["UserName"]+"!\"}";

            string callback = Request["callback"];
            Response.Write(callback + "(" + json + ")");
            Response.End();
        }

输出脚本,自动执行。

附:跨域请求的方式有很多种,

  1. iframe
  2. document.domain
  3. window.name
  4. script
  5. XDomainRequest (IE8+)
  6. XMLHTTPRequest (Firefox3.5+)
  7. postMessage (HTML5)
  8. 后台代理
  9. ServiceStack
  10. 等等...


参考:http://www.cnblogs.com/know/archive/2011/10/09/2204005.html

posted on 2016-03-08 16:35  邢帅杰  阅读(1791)  评论(0编辑  收藏  举报