【问题标题】:Backbone - performing multiple fetch() before rendering a viewBackbone - 在渲染视图之前执行多个 fetch()
【发布时间】:2013-02-19 16:46:06
【问题描述】:

我想知道这里的最佳模式/方法。这是我的路由器中的一个功能,因此用户点击“quotes/:id”,但要呈现该视图,我需要他们的项目、客户和货币的列表。在尝试实例化 quotesEdit 视图之前,确保所有 3 次 fetches() 都发生的最佳方法是什么?当用户点击某物时获取所有信息是否被认为是不好的做法?

    quotesEdit: function(id) {
        kf.Collections.quotes = kf.Collections.quotes || new kf.Collections.Quotes();
        kf.Collections.projects = kf.Collections.projects || new kf.Collections.Projects();
        kf.Collections.currencies = kf.Collections.currencies || new kf.Collections.Currencies();
        //do a fetch() for the 3 above
        kf.Collections.customers = kf.Collections.customers || new kf.Collections.Customers();
        var quote = kf.Collections.quotes.where({Id: parseInt(id, 10)});
        kf.Utils.ViewManager.swap('sectionPrimary', new kf.Views.section({
          section: 'quotesEdit',
          model: quote[0]
        }));
    }

【问题讨论】:

    标签: backbone.js


    【解决方案1】:

    我发现jQuery deferreds 和下划线的invoke 方法的组合可以优雅地解决这个问题:

    //call fetch on the three collections, and keep their promises
    var complete = _.invoke([quotes, projects, currencies], 'fetch');
    
    //when all of them are complete...
    $.when.apply($, complete).done(function() {
       //all ready and good to go...
    });
    

    【讨论】:

    • 默认情况下使用GET http 方法获取。我能写_.invoke([quotes, projects, currencies], 'fetch', {type: 'POST'})真是太棒了
    • 我已经为这个解决方案的这个特定实现搜索了几个小时。谢谢。
    • 我认为这个答案有点太聪明了。您必须了解_.invokefetchwhenapply 的行为。而@mrappleton 的答案是非常清楚的,即使对于对$.when 仅有模糊理解的人来说也是如此。
    • 自我注意:不像_.map,它对数组中的每个元素应用一个单个函数_.invoke允许我们调用一个方法 i> 函数在数组中的每个对象上,所以我们得到[quotes.fetch(), projects.fetch(), currencies.fetch()]。查看invoke 的Underscore 源代码并注意var func = isFunc ? method : value[method]; 这行给我们[quotes['fetch'], projects['fetch'], currencies['fetch']]
    • 不幸的是,这种美是肤浅的,而且这个解决方案是不必要的复杂,因为一个简单的$.when().then() 可以解决问题。
    【解决方案2】:

    承诺!具体jQuery.when

    你可以这样做:

    $.when(
      kf.Collections.quotes.fetch(),
      kf.Collections.projects.fetch(),
      kf.Collections.currencies.fetch()
    ).then(function(){
      // render your view.
    });
    

    jQuery.ajax(以及通过扩展骨干提取)返回一个承诺,一旦多个承诺得到解决,您可以使用$.when 设置回调函数。

    【讨论】:

    • 有效,我认为这比公认的答案更容易阅读
    【解决方案3】:

    Backbone 的 fetch 返回一个 jQuery Deferred 对象(一个承诺)。所以你可以使用 jQuery 的 when function 来等待所有的 Promise 解决:

    
    quotesEdit: function(id) {
      kf.Collections.quotes = kf.Collections.quotes || new kf.Collections.Quotes();
      kf.Collections.projects = kf.Collections.projects || new kf.Collections.Projects();
      kf.Collections.currencies = kf.Collections.currencies || new kf.Collections.Currencies();
    
      //do a fetch() for the 3 above
      var quotePromise = kf.Collections.quotes.fetch();
      var projectsPromise = kf.Collections.projects.fetch();
      var currenciesPromise = kf.collections.currencies.fetch();
    
      // wait for them to all return
      $.when(quotePromise, projectsPromise, currenciesPromise).then(function(){
    
        // do stuff here, now that all three have resolved / returned
    
        kf.Collections.customers = kf.Collections.customers || new kf.Collections.Customers();
        var quote = kf.Collections.quotes.where({Id: parseInt(id, 10)});
        kf.Utils.ViewManager.swap('sectionPrimary', new kf.Views.section({
          section: 'quotesEdit',
          model: quote[0]
        }));
    
      };
    
    }
    

    我在这里写了一些关于 Promise 和 jQuery 的内容:

    http://lostechies.com/derickbailey/2012/03/27/providing-synchronous-asynchronous-flexibility-with-jquery-when/

    http://lostechies.com/derickbailey/2012/07/19/want-to-build-win8winjs-apps-you-need-to-understand-promises/

    第二个链接仍然有效,尽管主要主题是 Win8 JS

    【讨论】:

    • 谢谢!每个人都在谈论“承诺”,但让我大吃一惊的是 @fencliff 的 _.invoke() 的巧妙使用!
    • 不需要的额外间接层,如果你问我:) ...但我想减少调用“fetch”三次会更漂亮一点
    • 如何在第二个等中使用第一个提取的输入? @DerickBailey
    猜你喜欢
    • 2015-02-25
    • 2018-04-21
    • 2020-11-14
    • 1970-01-01
    • 2020-09-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多