【问题标题】:JSON crossdomain communication with PHP file and a local javascript file与 PHP 文件和本地 javascript 文件的 JSON 跨域通信
【发布时间】:2011-11-03 07:04:24
【问题描述】:

我是 JSON 新手,但在 PHP 和 javascript 方面有很好的经验。问题很简单,答案可能更简单。我无法将服务器上的 PHP 文件中的数据发送到我在本地拥有的另一个 PHP 文件,该文件将从服务器接收 JSON 格式的数据。我做错了什么?

Javascript 片段(本地)

$(document).ready(function(){
//attach a jQuery live event to the button
$.getJSON('http://www.xpal.com/ws_users.php?action=get_user_data&user_id=33',function(data) {

        alert(data); //uncomment this for debug
        $('#showdata').html("<p>Username= "+data.username+"<br> Email= "+data.email+"<br> Firstname="+data.firstname+"<br> Lastname="+data.lastname+"</p>");
    });

});

PHP Frag(服务器@xpal.com):

$users=新用户;

if($_GET['action']=="get_user_data")
{
$user_id=$_GET['user_id'];
$assoc=array(
                "username"=>$users->return_username($user_id),
                "email"=>$users->return_user_emailid($user_id),
                "firstname"=>$users->return_user_firstname($user_id),
                "lastname"=>$users->return_user_lastname($user_id)
            );
echo json_encode($assoc);
}   

编辑:

错误信息:XMLHttpRequest 无法加载 xpal.com/ws_users.php?action=get_user_data&user_id=33。 Access-Control-Allow-Origin 不允许 Origin localhost。

【问题讨论】:

  • 据我所知没有。我跟踪了 URL,得到了一个不错的 JSON 字符串,其中包含用户数据(我希望是测试数据)。究竟出了什么问题。正在发生什么,您预计会发生什么?
  • XMLHttpRequest 无法加载 xpal.com/ws_users.php?action=get_user_data&user_id=33。 Access-Control-Allow-Origin 不允许来源localhost。是我得到的错误。是的,那是一个测试数据库:)
  • 这可能是由于您的浏览器的安全策略。请参阅:en.wikipedia.org/wiki/Same_origin_policy
  • 啊!我该如何着手解决这个问题?
  • 在这里阅读您的 cmets 以获得答案 我不清楚您对 xpal 服务器的访问权限。您是否在/为该服务器进行开发?

标签: php javascript jquery json


【解决方案1】:

您不能对托管页面的其他域进行 ajax 调用。请参阅浏览器出于安全原因实现的Same Origin Policy

有一种方法可以进行跨域 ajax 调用,它涉及使用JSONP。基本上,您将一个脚本标签注入到您自己的框架中,并且该脚本标签指向网络上任何地方的服务器端点。由于脚本标签的 src 值不受同源策略的限制,因此您可以访问该服务器。但是,现在您需要有一种方法来恢复该结果。这是使用 JSONP 完成的,您在服务器请求中指定您希望返回的 javascript 调用的 javascript 函数。返回的 javascript 中可以包含 javascript 数据,然后将其传递给所需的函数。 JSONP 需要客户端代码和服务器代码之间的合作,因为普通的 ajax 调用可能不支持 JSONP 的额外部分。但是,通过双方的合作,您可以绕过支持 JSONP 的服务器端点的同源策略。

【讨论】:

  • 感谢这位朋友。其他 API 是如何工作的?他们都使用JSONP?我想我所要做的就是从服务器端回显一个 JSON 包,并使用必要的 javascript 函数在客户端捕获它。看起来没那么容易。
  • @sniper - 我不明白你在评论中提出的问题。使用 ajax 与主机服务器通信很容易,因为这是同源。
  • 是的,我完全理解这一点。假设我希望 xpal.com 将数据发送到 facebook.com(一种方式)。所以 facebook.com 将需要对 xpal.com 进行一些 API 调用,而 xpal.com 会返回一个 JSON 对象,对吗?还假设一周后,xpal.com 应该将数据发送到我们正在构建的移动应用程序。这两种情况只有在我使用 JSONP 时才有可能?
  • 服务器可以随心所欲地相互交谈。它们不受同一来源的限制。但是,如果 xpal.com 上的页面想要与 facebook 通信,那么它可以使用为您管理跨域通信的 facebook API 来实现。如果在手机上查看的 xpal.com 网页想要与您自己的 xpal.com 服务器通信,它可以使用普通的 ajax 来实现,因为它是同源的。
【解决方案2】:

正如其他答案中已经解释的那样,由于Same Origin Policy,这不起作用。

现在,JSONP(参见 jfriend00 的回答)是一种解决方法,但它也有其缺点。 (见this page的结尾)。


还有另一种解决方法:让 PHP 查询远程服务器并将响应发送回客户端。请参阅此页面:

Cross domain AJAX querying with jQuery

此方法的主要缺点是所有流量都将通过您的服务器,因为您必须调用远程页面,获取响应将响应发送回客户端。

【讨论】:

  • 嘿NUE。我按照克里斯的建议做了。这是我的新代码行:PHP Frag:echo $_GET['callback']。 '('.json_encode($assoc).')'; JS FRAG : $.getJSON('xpal.com/…?', function(data) 这行得通!但这安全且正确吗?
  • @sniper 好吧,如果它有效,并且您知道 JSONP 的缺点,那么就去做吧。这里的主要安全问题是,这会使 你的 服务器受到来自 xpal.com 的潜在 XSS 攻击,但如果你足够信任它们,这应该不是问题。
【解决方案3】:

要使用 jsonp,正如其他人建议的那样,您必须要么输入 "callback=?"在 URL 的末尾,或使用 $.ajax() 并指定 dataType 为 jsonp。示例here

【讨论】:

  • 这就像一个桃子。 :) 但这是一个安全的解决方案吗?看起来它返回了一些即时可执行文件!
  • 据我了解,返回“一些即时可执行文件”正是 jsonp 的设计目的!见en.wikipedia.org/wiki/JSONP
【解决方案4】:

它被称为Same Origin Policy。简而言之:您的代码所在的域是您的 javascript 可以与之通信的唯一域(默认情况下)

JQuery won't get json?

【讨论】:

    【解决方案5】:

    如果可以的话,您可以在自己的服务器上运行 php 脚本。
    这:-

    <?php
        $details = file_get_contents('http://www.xpal.com/ws_users.php?action=get_user_data&user_id=33');
        var_dump(json_decode($details));
    

    返回这个:-

    object(stdClass)[1]
        public 'username' => string 'sniper' (length=6)
        public 'email' => string 'ajithsubramanian@gmail.com' (length=26)
        public 'firstname' => string 'Ajith' (length=5)
        public 'lastname' => string 'Ravi' (length=4)
    

    这会让你走上正确的道路吗?您可以在服务器上基于此对脚本进行 AJAX 调用。

    【讨论】:

    • 如果我正在构建一个 Web 服务,移动应用程序将使用该服务从我的服务器获取数据,该解决方案将如何扩展?我正在寻找一种解决方案,使其更像是最终返回结果的 API 函数调用。 :)
    • 您的问题中没有这些信息。但是,我认为它没有问题,由您以可扩展且健壮的方式编写代码。相信我,尝试在 jQuery 中执行此操作会遇到更多问题。
    【解决方案6】:

    您应该看看 CORS 及其实现。

    在您的情况下,可能的解决方案是在您的 php 文件中使用 header(Access-Control-Allow-Origin:http://localhost)。将 localhost 替换为 SOP 限制的域。

    可以在https://developer.mozilla.org/en/HTTP_access_control 找到有关 CORS 的良好参考。

    【讨论】:

      【解决方案7】:

      你可以使用同一个jQuery进行跨域请求,查看链接cross-domain request,他们有演示如何实现跨域请求...

      在您的代码中,请确保以下内容正确,

      • www.xpal.com 输出应为 json 格式
      • 如果您的输出中有任何错误,jsonp 技术不会显示错误(错误处理不佳)。

      • 你的 json 输出应该被 echo $_GET['callback']." ".json_encode($array).")";如上面提到的链接。

      【讨论】:

        猜你喜欢
        • 2012-01-28
        • 2017-09-15
        • 2011-07-05
        • 2012-06-28
        • 1970-01-01
        • 2011-07-24
        • 1970-01-01
        • 2013-03-13
        • 1970-01-01
        相关资源
        最近更新 更多