【问题标题】:"invalid label" when using JSONP?使用 JSONP 时出现“无效标签”?
【发布时间】:2012-04-22 11:10:32
【问题描述】:

我的 JSONP 请求有问题.. 数据不会显示,Firebug 显示“invalid label”错误..

我的 JavaScript:

$.ajax({
    url: link,
    dataType: "jsonp",
    beforeSend: function(xhr) {
        var base64 = btoa(username + ":" + password);
        xhr.setRequestHeader("Authorization", "Basic" + base64);
        xhr.overrideMimeType("application/json");
    },
    jsonpCallback: "getResources"
})

function getResources(data) {
    alert(data);
    alert(JSON.parse(data));
    $.each(data.groupStatus, function(i, item) {
        $("body").append("<p>ID: " + item.id + "</p>");
    });
}

我的 JSON:

{
    "groupStatus": [
        {
            "id": "Application Layer Configuration-ApplicationLayer",
            "time": 1332755316976,
            "level": 0,
            "warningIds": [],
            "errorIds": []
        },
        {
            "id": "Application Layer-ApplicationLayer:nscalealinst2",
            "time": 1333431531046,
            "level": 0,
            "warningIds": [],
            "errorIds": []
        }
    ]
}

我的 HTML:

<html>
<head>
    <title>Monitor</title>
    <link href="css/gadget.css" rel="stylesheet" type="text/css" />
    <script type="text/javascript" src="js/jquery-1.7.2.js"></script>
</head>
<body>
    <div id="content"></div>
    <script type="text/javascript" src="js/gadget.js"></script>
</body>

请求工作正常,但无论如何数据都没有显示。

我几天来一直在寻找解决方案。有人可以帮助我吗?提前谢谢!

解决方案(更新:06.09.12)

我已经解决了这个问题。执行的服务器(REST接口)没有实现回调函数.. 不使用 JSONP 设置跨域请求的另一种方法是设置以下 jquery 变量:

jQuery.support.cors = true;

【问题讨论】:

  • 这是因为 JSON 不是 一个有效的 JS 程序,但它正试图被用作一个。找出 JSONP 未按预期工作的原因。 (顺便说一句,getRessources 看起来像是拼写错误。)
  • 请求工作正常..我添加了响应的图像..
  • 响应不是 JSONP,而是 JSON。 JSONP 响应应该包装在像 callback({"foo": "bar"}) 这样的函数调用中
  • 您发送请求的服务器似乎不支持 JSONP 请求,或者您没有正确执行调用。

标签: javascript ajax json jsonp syntax-error


【解决方案1】:

对 JSONP 调用的响应需要将 JSON 本身包装在函数调用中,其中被调用函数的名称通常在 url 中提供。 jQuery 会自动将“回调”的查询字符串参数添加到正在请求的 URL,因此您服务器上的脚本应该执行类似于:

// assuming that $JSON contains your JSON content
print "{$_REQUEST['callback']}( {$JSON} );";

在响应中添加函数名称的原因是 JSONP 请求实际上是附加到 DOM 的脚本标记,而不是由 XMLHttpRequest 对象发出的常规请求。使用 JSONP 允许浏览器发出跨域请求,否则这些请求会被(默认情况下)应用于 XHR 的跨域策略阻止。

【讨论】:

  • 优秀的答案。只有一个补充。在我看来,有一个语法拼写错误——右大括号在错误的位置。必须打印 "{$_REQUEST['callback']( {$JSON} )};";
  • 这里 PHP 使用大括号将变量插入字符串,因此 {$_REQUEST['callback']}( {$JSON} ); 将在结果输出中打印为 someCallback( {"my": "JSON"} ),假设 $_REQUEST['callback']someCallback$JSON 等同于 array("my" =&gt; "JSON")
  • 啊,我明白了,你说得对。当您计划将比 $JSON 更复杂的变量(在这种情况下不需要大括号)(如数组)嵌入到字符串中时,这个大括号至关重要。
【解决方案2】:

如果 AJAX 脚本托管在同一个域上,那么您可以像这样使用dataType: "json"

function getResources(data, textStatus, jqXHR) {
    console.log(data);
    // no need to do JSON.parse(data)
    $.each(data.groupStatus, function(i, item) {
        $("body").append("<p>ID: " + item.id + "</p>");
    });
}
$.ajax({
    url: link,
    dataType: "json",
    beforeSend: function(xhr) {
        var base64 = btoa(username + ":" + password);
        xhr.setRequestHeader("Authorization", "Basic" + base64);
        xhr.overrideMimeType("application/json");
    },
    success: getResources
});​

如果 AJAX 脚本托管在另一个域中,则 服务器 必须返回 JSONP 数据——封装在函数调用中的 JSON 数据:

callback(
    {
        "groupStatus": []
    }
);​

如果服务器返回裸 JSON 数据,那么您将收到解析错误,因为 JSONP 请求与注入 &lt;script src="..."&gt; 标记大致相似。要了解为什么裸 JSON 对象字面量会导致解析错误,请考虑以下示例:

// WORKS
{
    alert("foo");
}

// PARSE ERROR -- quote from MDN:
// You should not use an object literal at the beginning of a statement.
// This will lead to an error or not behave as you expect, because the { 
// will be interpreted as the beginning of a block.
{
    "foo": "bar"
}

// WORKS
callback({
    "foo": "bar"
})​

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2010-10-18
    • 2013-01-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-02-19
    相关资源
    最近更新 更多