对于从 file:// URL 运行的应用程序发出的请求,“Access-Control-Allow-Origin 不允许使用 Origin null”错误

IT技术 javascript jquery xmlhttprequest cors jsonp
2021-01-20 21:14:39

我正在开发一个页面,通过 jQuery 的 AJAX 支持从 Flickr 和 Panoramio 中提取图像。

Flickr 端工作正常,但是当我尝试$.get(url, callback)从 Panoramio 运行时,我在 Chrome 的控制台中看到一个错误:

XMLHttpRequest 无法加载http://www.panoramio.com/wapi/data/get_photos?v=1&key=dummykey&tag=test&offset=0&length=20&callback=processImages&minx=-30&miny=0&maxx=0&maxy=150Access-Control-Allow-Origin 不允许 Origin null。

如果我直接从浏览器查询该 URL,它工作正常。这是怎么回事,我能解决这个问题吗?我是否错误地编写了我的查询,或者这是 Panoramio 阻止我尝试做的事情?

Google 没有在错误消息中找到任何有用的匹配项

编辑

下面是一些显示问题的示例代码:

$().ready(function () {
  var url = 'http://www.panoramio.com/wapi/data/get_photos?v=1&key=dummykey&tag=test&offset=0&length=20&callback=processImages&minx=-30&miny=0&maxx=0&maxy=150';

  $.get(url, function (jsonp) {
    var processImages = function (data) {
      alert('ok');
    };

    eval(jsonp);
  });
});

您可以在线运行该示例

编辑 2

感谢 Darin 在这方面的帮助。 上面的代码是错误的。 改用这个:

$().ready(function () {
  var url = 'http://www.panoramio.com/wapi/data/get_photos?v=1&key=dummykey&tag=test&offset=0&length=20&minx=-30&miny=0&maxx=0&maxy=150&callback=?';

  $.get(url, function (data) {
    // can use 'data' in here...
  });
});
6个回答

作为记录,据我所知,您有两个问题:

  1. 您没有将“jsonp”类型说明符传递给您的$.get,因此它使用的是普通的 XMLHttpRequest。但是,您的浏览器支持 CORS(跨域资源共享)以允许跨域 XMLHttpRequest,如果服务器通过了它。这就是Access-Control-Allow-Origin标题进来的地方

  2. 我相信您提到您是从 file:// URL 运行它的。CORS 标头有两种方式来表示跨域 XHR 正常。一个是发送Access-Control-Allow-Origin: *(如果你通过 到达 Flickr $.get,他们一定已经在做),而另一个是回显Origin标题的内容但是,file://URL 会产生一个Origin无法通过回显授权的空值

Darin 建议使用$.getJSON. 如果它看到callback=?URL 中的子字符串,将请求类型从默认的“json”更改为“jsonp”会有点神奇

通过不再尝试从file://URL执行 CORS 请求,解决了第二个问题

为了向其他人澄清,这里是简单的故障排除说明:

  1. 如果您尝试使用 JSONP,请确保是以下情况之一:
    • 您正在使用$.get并设置dataTypejsonp.
    • 您正在使用$.getJSON并包含callback=?在 URL 中。
  2. 如果您尝试通过 CORS 执行跨域 XMLHttpRequest ...
    1. 确保您正在通过http://. 通过运行的脚本file://对 CORS 的支持有限。
    2. 确保浏览器确实支持 CORS(Opera 和 Internet Explorer 迟到了)
如果以参数 --allow-file-access-from-files 开头,则某些浏览器(例如 chrome)允许 CORS
2021-03-10 21:14:39
callback=?没有为我工作,但jsonp=?做了。对此有什么解释吗?
2021-03-18 21:14:39
@crunkchitis:我不确定为什么callback=?不适合你,因为当前的 jQuery 文档仍然说它应该,但是,如果我正确阅读它们,他们也说这anything_else=?也可以。
2021-03-25 21:14:39
那么解决这个问题的方法是什么?
2021-04-02 21:14:39

您可能需要在被调用的脚本中添加一个 HEADER,这是我必须在 PHP 中执行的操作:

header('Access-Control-Allow-Origin: *');

跨域 AJAX ou services WEB(法语)中的更多详细信息

对于一个简单的 HTML 项目:

cd project
python -m SimpleHTTPServer 8000

然后浏览您的文件。

在 Google Chrome v5.0.375.127 上对我有用(我收到警报):

$.get('http://www.panoramio.com/wapi/data/get_photos?v=1&key=dummykey&tag=test&offset=0&length=20&callback=?&minx=-30&miny=0&maxx=0&maxy=150',
function(json) {
    alert(json.photos[1].photoUrl);
});

此外,我建议您改用该$.getJSON()方法,因为以前方法不适用于 IE8(至少在我的机器上):

$.getJSON('http://www.panoramio.com/wapi/data/get_photos?v=1&key=dummykey&tag=test&offset=0&length=20&callback=?&minx=-30&miny=0&maxx=0&maxy=150', 
function(json) {
    alert(json.photos[1].photoUrl);
});

您可以从这里在线试用


更新:

现在你已经展示了你的代码,我可以看到它的问题。您同时拥有匿名函数和内联函数,但两者都将被调用processImages这就是 jQuery 的 JSONP 支持的工作原理。请注意我如何定义callback=?以便您可以使用匿名函数。您可以在文档中阅读更多相关信息

另一个注意事项是你不应该调用 eval。传递给匿名函数的参数已经被 jQuery 解析为 JSON。

我得到 Uncaught TypeError: $.get is not a function at <anonymous>:1:3
2021-03-16 21:14:39

只要请求的服务器支持JSON数据格式,就使用JSONP(JSON Padding)接口。它允许您在没有代理服务器或花哨的标题内容的情况下发出外部域请求。