【问题标题】:JQuery Ajax success callback not work when building array of Ajax calls构建 Ajax 调用数组时,JQuery Ajax 成功回调不起作用
【发布时间】:2016-04-05 21:19:20
【问题描述】:

我需要通过解析基于另一个数组构建的承诺数组来构建对象数组。

假设我有一个letters = ['a', 'b', 'c'] 数组。然后,我将它映射为使用每个字母作为参数进行 Ajax 调用,如下所示:

var result = letters.map(function (letter) {
    return $.getJSON('myuri', { param: letter });
};

结果,我得到了一个带有 ajax 承诺的数组。然后我像这样解决它:

Promise.all(result).then(function (response) {
    console.log(response);
});

日志正在打印每个 ajax 调用的原始响应。在那之前一切都很好。但我不想要原始响应,我想要自定义对象,所以我尝试使用 Ajax 的成功回调来创建它们,如下所示:

var letters = ['a', 'b', 'c'];

var result = letters.map(function (letter) {
    return $.getJSON('myuri', { param: letter })
            // Chaining with success callback
            .done(function (response) {
                return {
                    'custom_attr': response.x,
                    'athor_custom_attr': response.y
                };
    });
});

Promise.all(result).then(function (response) {
    console.log(response);
});

问题是成功回调不会干扰数组的创建。实际上,我可以在回调中将返回值更改为 ANYTHING 并没有任何区别,代码仍然返回原始响应的数组。

当我使用 Angular 使用 $http 服务时,它运行良好,但使用 $.getJSON 的 JQuery 不起作用,我不明白为什么会发生这种情况。

提前谢谢大家。

【问题讨论】:

标签: javascript jquery angularjs ajax promise


【解决方案1】:

您的回调返回值被忽略,因为您使用了done。您真正想要的是使用 then 为回调结果创建一个新的承诺:

var result = letters.map(function (letter) {
    return $.getJSON('myuri', { param: letter })
        .then(function (response) {
            return {
                'custom_attr': response.x,
                'athor_custom_attr': response.y
            };
        });
});

done 方法不可链接!几乎没有理由使用它而不是 then

【讨论】:

  • 成功了!我之前用过then,结果是一样的。但现在我只是工作。谢谢。
  • 有趣,不知道done 不可链接。谢谢!
  • @romellem:嗯,从技术上讲,您可以将更多方法调用链接到它,因为它返回了调用它的承诺,但它在单子意义上是不可链接的。
【解决方案2】:

正如我在评论中提到的,我认为您只需将每个 jqXHR 的响应数据映射到您想要的自定义对象。

比如:

Promise.all(result).then(function (response) {
    result = response.map(function(c) {
        return {
            'custom_attr': c.x,
            'another_custom_attr': c.y
        };
    });
});

这是假设 var result; 声明在一个可在此处访问的范围内。


这是一个完整的示例:

<!-- index.html -->
<button class="load-ajax">Click To Make our AJAX calls!</button>
<script src="jquery.min.js"></script>

<script>
// Declare `result` in global scope.
var result;

$(document).ready(function() {
    $('.load-ajax').on('click', function(e) {
        e.preventDefault();

        var letters = ['a', 'b', 'c'];
        result = letters.map(function (letter) {
            return $.getJSON('json.php', { param: letter });
        });

        Promise.all(result).then(function (response) {
            result = response.map(function(c) {
                return { "custom_attr" : c.param };
            });
            console.log("DONE! Look at `result`");
        });
    });
});
</script>

还有样本json.php文件:

<?php
// json.php
header('Pragma: no-cache');
header('Cache-Control: no-store, no-cache, max-age=0, must-revalidate');
header('Content-Type: application/json');

echo json_encode($_GET);
?>

所以,归根结底,result 等于:

[
  {custom_attr: "a"},
  {custom_attr: "b"},
  {custom_attr: "c"}
]

【讨论】:

  • 我尝试了您的代码并再次迭代也解决了问题。但我想避免再次迭代,特别是因为在 Angular 中我不需要这样做,我想知道为什么我会使用 JQuery。谢谢!
猜你喜欢
  • 2014-07-08
  • 1970-01-01
  • 2014-08-13
  • 1970-01-01
  • 1970-01-01
  • 2017-06-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多