jsonp不一致错误:对象不是函数

Yak*_*ako 7 ajax jquery jsonp

我正在尝试将jsonp与jQuery一起使用但是我的行为不一致.有时脚本有效,有时却没有; 我真的不明白为什么.

这是Chrome可能显示的错误:

Uncaught TypeError: Property 'jQuery18208278296771459281_1362854738133' of object [object Object] is not a function
Run Code Online (Sandbox Code Playgroud)

在以下示例中,我只是尝试检查应用程序是否在线.但是这种不一致的行为可能发生在其他类似的ajax调用上:

     $.ajaxSetup({
        error: function (req, status, ex) {},
        success: function (data, status, req) {},
        timeout: 2000,
        crossDomain: true,
        contentType: "application/json",
        dataType:"jsonp",
        url: "http://myUrl.com/ping.php?preventCache="+new Date()
    });
    return $.ajax();
Run Code Online (Sandbox Code Playgroud)

服务器端PHP文件也很简单:

<?php
header("Content-Type: application/javascript; charset=UTF-8");
echo $_GET['callback'];
?> ({ "status": "online" })
Run Code Online (Sandbox Code Playgroud)

Dan*_*ird 15

当您的JSONP调用超时(根据您的timeout: 2000行,这是两秒),您将得到此行为,但数据在超时发生后到达.

JSONP不使用普通的XmlHTTPRequest.要做JSONP,jQuery会在文档中插入一个脚本标记,并创建一个临时函数来处理脚本标记加载(函数名称是错误消息中的长随机字符串).

当您的超时发生且脚本尚未完成加载时,jQuery会丢弃临时函数.之后的某个时候,脚本标记完成加载,并尝试调用该函数 - 但为时已晚,该函数已被删除.因此错误.

通过延长超时可能会减少错误,但基本问题是您无法取消加载脚本标记.如果它没有出错,那么它总是有可能比你的超时花费更长的时间.据我所知,这方面没有简洁的解决方案.你可以告诉jQuery使用一个显式命名的函数作为JSONP回调而不是自己创建,但是你需要跟踪自己是否超时.你可以使用CORS,这是另一回事.

可能你最好的选择就是忍受它.


小智 5

你的问题不是那么清楚,当我试图两次使用相同的回调函数名时,我得到了同样的错误.在任何情况下,这是如何在jquery中调用jsonp:

      var mycallback = 'c'+Math.floor((Math.random()*100000000)+1);
      $.ajax({
                   type: 'GET',
                    url: URL,
                    async: true,
                    jsonpCallback: mycallback,
                    contentType: "application/json",
                    dataType: 'jsonp'

       }).done(function(json){
           console.log(json);
                    callback(json);
       }).fail(function(f){
           console.log("f");
                    console.log(f.status);
       }).always(function(){
                   // console.log('complete');
      }); 
Run Code Online (Sandbox Code Playgroud)