javascript - 带有动态 Url 的 jQuery $.Deferred()

标签 javascript jquery caching promise

我开始重构一些代码以使用 promise 和缓存来确保代码更干净。我的代码(见下文)尝试使用这个新前提,并且取得了轻微的成功。主要问题是,默认使用的缓存机制阻止我“传递”动态 url 值,而不会每次都返回相同的缓存结果。如何更新下面的代码以使用缓存 key ?

"use strict";

var FLEX = window.FLEX|| {};
FLEX.Following = FLEX.Following|| {}; 

FLEX.Following.Process = function () {

var deferred = $.Deferred(),
execute = function (followUrl) {
    $.ajax(
            {
                url: _spPageContextInfo.webAbsoluteUrl +
                    followUrl,
                method: "GET",
                headers: {
                    "accept": "application/json;odata=verbose",
                },
                success: function (data) {
                    deferred.resolve(data);
                },
                error: function (err) {
                    deferred.reject(err);
                }
            }
        );
    return deferred;
};
return {
    execute: execute
}

}();

FLEX.Following.Init = function (divName, followUrl) {
FLEX.Following.Process.execute(followUrl).promise().then(

    //success
    function (data) {
        var html = "";
        $.each(data.d.Followed.results,function(index, value){
           html += value.Name + "<br />";
        });

        $(divName).html(html);

    },

    //failure
    function(err) {
        $(divName).html('Failed');
    }   
);             
}

然后我使用以下几行调用代码:

    $(document).ready(function() {
        FLEX.Following.Init("#followed-sites", "/_api/social.following/my/followed(types=4)");
        FLEX.Following.Init("#followed-people", "/_api/social.following/my/followed(types=1)");
        FLEX.Following.Init("#followed-documents", "/_api/social.following/my/followed(types=2)");     
    });

结果输出“有效”,但是我在每个 div 中得到相同的结果,因为似乎每个后续调用 jQuery 都会从其中之一获取缓存版本,因此每个结果集都是相同的。我怎样才能确保我可以使用与上面不同的动态网址相同的功能并单独缓存它们。

谢谢

最佳答案

我认为根本问题是您创建了一个 $.Deferred(),然后尝试重用它来多次调用 execute() 并且获胜从来没有工作过。延迟是一次性触发。一旦它被履行或拒绝,它就会保持这种状态并永远包含相同的数据。如果您希望后续调用得到不同的结果,则必须为每个调用创建一个新的延迟。因此,因为您是在 execute() 函数之外创建延迟的,所以您只有一个延迟,因此第一个结果将永远保留。

此处的修复方法是为每次调用 execute() 使用单独的 Promise/Deferred。由于 $.ajax() 已经在每次调用时返回一个新的 Promise - 您可以使用它,而不是手动创建自己的 $.Deferred (这是一种反模式) 。让我们立即重构并解决这两个问题。

这是您重构的函数,请解决这些问题:

var execute = function (followUrl) {
    return $.ajax({
         url: _spPageContextInfo.webAbsoluteUrl + followUrl,
         method: "GET",
         headers: {"accept": "application/json;odata=verbose"}
    });
};

然后,在这行代码中:

FLEX.Following.Process.execute(followUrl).promise().then(

您应该删除 .promise() 因为我上面的更改已经返回了一个 promise ,因此这一行可以变成这样:

FLEX.Following.Process.execute(followUrl).then(

关于javascript - 带有动态 Url 的 jQuery $.Deferred(),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25856233/

相关文章:

javascript - 拖放文本练习

javascript - 在 Android 浏览器上,在文本框内输入时整个页面会上下跳动?

javascript - 如何使固定元素在滚动时隐藏,然后在用户不滚动时出现

JavaScript 不从缓存加载文件

asp.net-mvc - ASP.NET MVC 4.0 Chrome 缓存

javascript - 如何在拖动开始时返回父元素编号

javascript - 根据屏幕尺寸的视口(viewport)值

javascript - Bootstrap - 如何缩小图像以适应窗口高度?

javascript - 通过tr id从同一个表中读取td值

Python:math.factorial 是否已内存?