繁体   English   中英

在解析其他多个延迟的对象之后解析延迟的对象

[英]Resolve deferred object after other multiple deferred objects are resolved

我对$.Deferred经验非常有限,到目前为止,附带的代码看起来非常混乱。

本应返回承诺的函数是使用ajax请求后收到的HTML更新DOM。

它的用法如下:

this._refreshWorkspace(response.html).then(function(){
  // do things after DOM update finished
});

这是功能代码:

_refreshWorkspace: function(htmlBlocks){

  var dfd = $.Deferred();

  if('editor' in htmlBlocks){
    app.destroy(this.editor).then((function(){
      this.editor.empty().append(htmlBlocks.editor);
    }).bind(this)).then((function(){
      app.refresh(this.editor);
    }).bind(this));
  }

  if('listPanels' in htmlBlocks){
    app.destroy(this.list).then((function(){
      this.list.empty().append(htmlBlocks.listPanels);
    }).bind(this)).then((function(){
      app.refresh(this.list);
      // other unrelated code here
      dfd.resolve();

    }).bind(this));
  }

  if('listNav' in htmlBlocks){
    // similar code block       
  }

  return dfd;
},

它似乎有效,但是只有在提供了“ listPanels” htmlBlock的情况下。 我希望在所有刷新调用之后对dfd进行一次解析,或者,如果可能的话,甚至在所有刷新调用都解决后甚至更好。 关于如何实现此目标的任何想法?

将循环中的所有promise放入数组中,然后使用$.when 可悲的是,在数组中使用$.when很丑陋:

return $.when.apply($, theArray);

...因为$.when被设计为接受离散参数而不是数组。

像这样:

_refreshWorkspace: function(htmlBlocks){

  var promises = [];

  if('editor' in htmlBlocks){
    promises.push(
      app.destroy(this.editor).then((function(){
        this.editor.empty().append(htmlBlocks.editor);
      }).bind(this)).then((function(){
        app.refresh(this.editor);
      }).bind(this))
    );
  }

  if('listPanels' in htmlBlocks){
    promises.push(
      app.destroy(this.list).then((function(){
        this.list.empty().append(htmlBlocks.listPanels);
      }).bind(this)).then((function(){
        app.refresh(this.list);
      }).bind(this))
    );
  }

  if('listNav' in htmlBlocks){
    // similar code block       
  }

  return $.when.apply($, promises);
},

这是一个使用随机Deferred的实时示例:

 function doSomething() { var promises = []; var d1, d2, d3; d1 = new $.Deferred(); promises.push(d1.promise()); setTimeout(function() { snippet.log("Resolving d1"); d1.resolve(1); }, Math.floor(Math.random() * 1000)); d2 = new $.Deferred(); promises.push(d2.promise()); setTimeout(function() { snippet.log("Resolving d2"); d2.resolve(2); }, Math.floor(Math.random() * 1000)); d3 = new $.Deferred(); promises.push(d3.promise()); setTimeout(function() { snippet.log("Resolving d3"); d3.resolve(3); }, Math.floor(Math.random() * 1000)); return $.when.apply($, promises); } // Use it doSomething().then(function() { snippet.log("All resolved"); }); 
 <!-- Script provides the `snippet` object, see http://meta.stackexchange.com/a/242144/134069 --> <script src="http://tjcrowder.github.io/simple-snippets-console/snippet.js"></script> <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script> 

如前所述,该问题的简单答案是将单个诺言与$.when.apply(null, promiseArray)

但是,如果问题中的所有代码都代表要应用于所有html块的处理方式,那么您可以走得更远。

jQuery.map()将在对象的ownProperties上运行,因此可以利用它在htmlBlocks上进行迭代,从而产生简洁,通用的主例程,并带有两个支持的哈希。

_refreshWorkspace: function(htmlBlocks) {
    var that = this; // avoids the need for .bind(this) in the promise chain and the methodsHash
    var propHash = {
        'editor': 'editor',
        'listPanels': 'list'
    };
    // All the "other unrelated code" is defined here
    var methodsHash = {
        'editor': null,
        'listPanels': function(key, obj) {
            ...
        },
        ...
    };
    //And the main routine is a concise $.map(htmlBlocks, ...) structure. 
    var promises = $.map(htmlBlocks, function(html, key) {
        var obj = that[propHash[key]];
        return app.destroy(obj).then(function() {
            obj.empty().append(html); //if empty() and append() are jQuery methods then this line is synchronous.
            return app.refresh(obj);// if app.destroy() is asynch and theanable, then it seems safe to assume that app.refresh() is also asynch and theanable. Therefore return the result here.
        }).then(function() {
            if(methodsHash[key]) {
                methodsHash[key](key, obj);
            }
        });
    });

    //Now aggregate `promises` into a single promise which resolves when all the promises resolve, or rejects when any of the promises rejects.
    return $.when.apply(null, promises);
},

现在,为了满足所有其它的HTML代码,只需添加一行到propHash和一个空的或功能methodsHash 如果主要例程是全面的,则无需修改。

恕我直言,这是组织代码的更好方法。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM