JSONP:需要回调吗?

Posted

技术标签:

【中文标题】JSONP:需要回调吗?【英文标题】:JSONP: Is a callback necessary? 【发布时间】:2012-08-02 11:44:12 【问题描述】:

我正在使用 AJAX、jQuery 和 Phonegap 创建一个 ios / Droid 应用程序。后端是通过 Web 服务提供内容的 Drupal 7 站点。不过,我对 JSONP 回调的必要性有点困惑。

我的理解是,为了允许跨域请求,需要 JSONP。而且,在某种程度上,它通过将 JSON 数据包装在回调函数中来工作,从而使其成为一个对象。

但是,我发现我可以在没有回调的情况下发送 JSONP 请求,并通过 jQuery 解析数据而无需回调函数。所以 JSONP 数据看起来和 JSON 数据一模一样。

我错过了什么吗?如果将数据作为函数提供是 JSONP 的好处之一,那么在流程的某个阶段不应该需要它吗?我是否通过不发送回调参数来绕过某种级别的安全性?

谢谢!

仅供参考,这里是 jQuery AJAX 代码:

$.ajax(
    type: 'GET',
    cache: false,
    url: 'http://www.example.com/mobile/menu/devel-gosto.jsonp',
    dataType: 'jsonp',
    timeout: menuLoadTimeout,
    success: function (data) 
        menu = populateSlider(data.tree, 0);
    
); 

所以我将 dataType 设置为“jsonp”,调用返回 JSONP 数据的 Web 服务,但将回调排除在 URL 之外。 Web 服务在没有回调包装器的情况下进行响应。一切正常。

【问题讨论】:

如何使用 jQuery 解析 JSON-not-P 数据?你能给我们举个例子吗? 您的“ajax 调用”是否与提供 html 的域相同? ...或者它是否支持 CORS?而jQuery会自动检测MIME类型并解析JSON而不是执行脚本? 确定 jquery 不会自动生成回调并将回调添加到请求 url 中吗? 32bitkid:你解开了我的谜团。服务器日志显示,如果我没有指定,jQuery 确实将回调添加到 URL。我在 Firebug 中没有注意到它。谢谢! 【参考方案1】:

如果没有回调,JSONP 调用将无法工作。数据加载在script标签中,如果代码不是方法调用的形式,结果只是一个被丢弃的对象,永远不会调用success回调方法。

ajax 方法正在向 URL 添加一个回调参数,即使您没有指定一个。

在文档中,dataType 设置的 "jsonp" 值下:

“在 URL 的末尾添加一个额外的“?callback=?”以指定 回调。”

http://api.jquery.com/jQuery.ajax/

【讨论】:

啊,我应该有 RTFM。谢谢,古法。 :)【参考方案2】:

JSONP 是为响应同源策略 (SOP) 而设计的,该策略指出,如果 HTML 页面是从一个域提供的,那么网页(一旦交付给客户端)就不能进行“Ajax 调用”不同域上的站点。如果对同一个域进行了“Ajax 调用”,那么一切都很好。 (也许是你看到的?)

现在,您不能对不同的域进行 Ajax 调用,但您可以使用脚本标记来调用不同域上的代码(看图,嗯?)。现在的问题是,假设您在脚本标签中调用了一个不同的域,并返回了一些 JSON 文本。你会如何它?这就是 JSONP 的用武之地。如果服务器发回一些包装在函数调用中的 JSON,那么当您评估该(包装的)对象时,您现在正在“用它做一些事情”。

不过,最近大多数浏览器都支持CORS,因此不再需要 JSONP。然而,一些较旧的浏览器不支持 CORS,但是这些越来越少。

【讨论】:

具有讽刺意味的是,一旦我编译,JSON 就很好,因为 Phonegap 没有跨域安全问题。所以对于开发人员,我想我应该研究一下 CORS。我还没有找到在我的开发环境中调用它的可靠方法。【参考方案3】:

需要回调吗?

是的,当然。回调对于JSON-with-padding 的定义是实质性的。没有,它只是 JSON。

【讨论】:

【参考方案4】:

是的,这是必需的。默认函数名是callback,但可以是任何声明的函数名。

https://jar-download.com/java-documentation-javadoc.php?a=jersey-json&g=com.sun.jersey&v=1.19.2

它为我们提供了一种访问返回数据的方法。它通过让服务器返回包装在函数调用(“填充”)中的 JSON 数据来实现这一点,然后浏览器可以解释这些数据。此函数必须在评估 JSONP 响应的页面中定义。

see here

【讨论】:

以上是关于JSONP:需要回调吗?的主要内容,如果未能解决你的问题,请参考以下文章

使用 jQuery 请求 JSONP 时,我可以使用静态(即预先确定的)回调函数名称吗?

JSONP回调不起作用

封装一个JSONP请求

JSONP 回调给全局变量赋值失败解决

JSONP实现跨域

Jsonp 复习笔记