【问题标题】:Using ajax long polling to update a response on my page from an external API使用 ajax 长轮询从外部 API 更新我的页面上的响应
【发布时间】:2016-09-04 21:33:06
【问题描述】:

我有以下 ajax 长轮询脚本

(function poll(){
    $.ajax({ url: "<?php echo URL::to('/internal/v1/checkTxn');  ?>", success: function(data){
        //Update your dashboard gauge
        console.log(data.status);  //Data is getting logged
        if(data.status == 'success'){  //This condition is not being checked
            console.log('suucesful'); //Not coming
        }
    }, dataType: "json", complete: poll, timeout: 1000 });
})();

后端PHP代码如下

 if(isset($_POST['status']) && $_POST['status']){
            $data = ['status'=>$_POST['status']];
            $json = json_encode( $data );
           echo $json;
        }

流程

  1. 当我呈现页面时,ajax 脚本运行并等待响应。当我检查网络选项卡时,ajax 无休止地向指定的 URL 发出请求。

  2. 我从外部网站收到一个表单帖子到后端 PHP,我需要将其推送到 jquery。

但是,当发布帖子时,控制台中不会记录任何内容。但是如果我在 $json 中硬编码一些值并回显它,它就会出现在控制台中。

我面临两个问题

  1. 当一个帖子发生在 PHP 脚本上时,它不会出现在 ajax 代码中。

  2. 当我对 $json 进行硬编码(模拟外部表单发布的响应)并回显它时,它会出现在控制台中,但是 data 的条件.status== 'success' 没有得到检查。

这有什么问题。我错过了什么吗?

更新

I could fix the "condition not being checked" as there was something wrong the json being echoed.

Now to avoid confusion, the flow for this

User open the page, 

> The ajax starts the long polling process to my PHP code, waiting for a
> response.User enters payment details in a form which is my html,clicks on pay, a pop up appears
> which renders the banks login page (Payment gateway).After user entering all
> details in the pop up (banks page), bank sents a server to server call about the status of
> transaction to my notificationURL
> ('mydomain.com/internal.v1/checkTxn'). As soon as I get a POST on this
> URL(I will close the pop up), my ajax polling should get the data posted to my PHP and there by
> I will show the status of TXN to the user on the same card form he entered his details earlier and
> the pop window closes. The response here is returned by my PHP code to the ajax.
The
> post coming to my PHP code is a server to server post which is posted
> by a Payment Gateway.

【问题讨论】:

  • 你应该做 JSON.parse(data) 在成功时将它们转换为 ajax 中的 JS 对象,因为你在 JSON 中获取数据,我猜 (function(){...}(jQuery); 你必须将 jQuery 作为参数传递给 IIFE
  • 从外部站点发布可能无法正常工作。 Ajax 通常仅限于同一个站点。
  • @Brett 不,expernal 站点发布到我的 PHP 脚本,然后 ajax 调用我服务器上的 php 脚本

标签: javascript php jquery ajax long-polling


【解决方案1】:

1.让我们调试一下:

设置你的ajax错误回调,

$(function(){

        (function poll(){
            $.ajax({ url: "http://tinyissue.localhost.com/test.php", success: function(data){
                //Update your dashboard gauge
                console.log(data.status);  //Data is getting logged
                if(data.status == 'success'){  //This condition is not being checked
                    console.log('suucesful'); //Not coming
                }
            },error:function(err){
                console.info('error fired...');
                console.info(err);
            }, dataType: "json", complete: poll, timeout: 1000 });
        })();

    });

运行这个,你会得到控制台

error fired...
Object {readyState: 4, responseText: "", status: 200, statusText: "OK"}

2。为什么要去错误回调:

为什么 ajax 响应 status200statusText"OK"error 回调仍然被触发而不是 success

您的 AJAX 请求包含以下设置:

dataType: "json"

documentation 声明 jQuery:

将响应评估为 JSON 并返回一个 JavaScript 对象。 (...) JSON数据被严格解析;任何格式错误的 JSON 都是 被拒绝并抛出解析错误。

这意味着如果服务器返回 invalid JSON 并带有 200 OK 状态,那么 jQuery 会触发错误函数并将 textStatus 参数设置为“parsererror”。

解决方案:确保服务器返回有效的 JSON。值得注意的是,空响应也被认为是无效的 JSON;例如,您可以返回 {} 或 null 验证为 JSON。

3.为什么 ajax 返回无效的 JSON:

在您的脑海中,在服务器端,您检查了$_POST['status'] 以确保循环轮询中的最后一次调用成功,仅设置了$_POST['status'],您将回显json,或者它什么都不回显。

但是,不幸的是,在调用循环开始时,第一次调用 ajax,您没有将 status 设置为发布。然后它什么都没有回显,然后它去了error回调,也去了complete回调,然后在没有status的情况下再次调用发布。看,这是一个糟糕的循环。

4.解决方案:

设置 status 值以在第一次 ajax 调用时发布。

$(function(){

        (function poll(){
            var status = 'success';
            $.ajax({ url: "http://tinyissue.localhost.com/test.php", success: function(data){
                //Update your dashboard gauge
                console.log(data.status);  //Data is getting logged
                status = data.status;
                if(data.status == 'success'){  //This condition is not being checked
                    console.log('suucesful'); //Not coming
                }
            },error:function(err){
                console.info('error fired...');
                console.info(err);
                status = 'error';
            }, type:'post',dataType: "json", data:{status:status}, complete: poll, timeout: 1000 });
        })();

    });

【讨论】:

  • 我认为这很混乱。 POST 不是由 Ajax 完成的。它由外部表单帖子完成。 AJAX-> POLLING->PHP
  • 我可以修复没有响应的问题。仍然存在无法获取外部表单发布的数据的问题。
  • 有点困惑...从客户端到服务器的每个连接都为自己创建$_POST,ajax 请求如何获取表单发布请求的$_POST 变量?这是不可能的...或者我误会了吗?
  • 我猜你被误解了。我会更新问题
  • 我最后更新了问题,请看流程
【解决方案2】:

如果您使用长轮询,您可能会遇到缓存问题。 首先,当您的帖子进入您的系统时,检查 checkTxn 是否更改。 最后,您可以在url查询中添加一个随机参数(例如通过添加以毫秒为单位的日期),您不会使用它,但您的服务器会认为您的请求不同。

请检查并告诉我们。

@Edit:当然@Ajeesh,我会解释它:

(function poll(){
    $.ajax({ url: "<?php echo URL::to('/internal/v1/checkTxn');  ?>?_ts=" + new Date().getTime(), success: function(data){
        //Update your dashboard gauge
        console.log(data.status);  //Data is getting logged
        if(data.status == 'success'){  //This condition is not being checked
            console.log('suucesful'); //Not coming
        }
    }, dataType: "json", complete: poll, timeout: 1000 });
})();

这样做不会使用缓存,因为您的服务器/浏览器的所有查询都不同。

另一方面,当您收到 POST 时,我要求您对页面进行任何更改,因此,如果没有,您的 ajax 将永远不会收到通知,您知道我的意思吗?

【讨论】:

  • @Tisktkle 你能详细说明一下吗?
  • 通过关注您的 cmets,不可能从您的 ajax 投票中获得页面中的 POST 请求,或者至少不是一件容易的事。您的 ajax 正在从页面呈现过程中获取 html/json 数据。如果您不更改页面数据,它将永远收到相同的数据。
猜你喜欢
  • 1970-01-01
  • 2023-03-03
  • 1970-01-01
  • 2012-02-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-04-20
  • 2014-08-10
相关资源
最近更新 更多