2016-07-02 64 views
0

我想學習如何使用藍鳥承諾,我有點失落。通過函數返回承諾異步映射集合

我有兩個數據庫表:topicsubject

topic表有一個subject_id列,然後可以使用該列查詢主題標題的subject表。

我有一個orm異步查詢並返回一個承諾。

最後我想寫的主題,也確實查找對你來說,注射subject_title從隨後subject查詢到最初從topic查詢返回的對象的數組中的每個元素返回模型的方法。我試圖使用Promise.map,但這是行不通的。下面的代碼不起作用。我從來沒有想到它,但我認爲它捕捉了我想要完成的本質。

var promise = orm.select({ 
    db:  db, 
    table: 'topic', 
    where: args.where, 
    order: args.order, 
    limit: args.limit, 
    offset: args.offset, 
    group: args.group 
}).map(function (topic) { 
    var promise = orm.select({ 
     db: db, 
     table: 'subject', 
     qrm: 'one', 
     where: {id: topic.subject_id} 
    }).then(function (subject) { 
     topic.subject_title = subject; 
    }); 
    return promise; 
}); 

return promise; 

因此,假設一個香草topic對象具有的屬性:

[subject_id, title, description] 

而一個subject對象具有:

[id, title] 

我想上述函數返回對象的數組具有以下屬性:

[subject_id, subject_title, title, description] 

完成此操作最簡潔的方法是什麼?

+0

爲什麼不避免突變,並返回一個新的對象與你的新屬性? – elclanrs

+1

'orm.select()'返回什麼?它是否恢復了藍鳥的承諾?而且,實現的數據是什麼? – jfriend00

+0

@ jfriend00它返回一個藍鳥的承諾。 fufilled數據是一組對象。數組中的每個對象表示'topics'表中的一行。 – LukeP

回答

1

看來,你只是需要從.then()處理程序返回修改後的topic對象,使其保持在履行值:

return orm.select({ 
    db:  db, 
    table: 'topic', 
    where: args.where, 
    order: args.order, 
    limit: args.limit, 
    offset: args.offset, 
    group: args.group 
}).map(function (topic) { 
    return orm.select({ 
     db: db, 
     table: 'subject', 
     qrm: 'one', 
     where: {id: topic.subject_id} 
    }).then(function (subject) { 
     topic.subject_title = subject; 
     // Add return here so topic stays the fulfilled value 
     return topic; 
    }); 
}); 

頂級承諾的fullfilled值應修改主題對象的數組。

+0

哦!你說得對,那是有效的。我的假設是,我最終會得到一組promise,而不是一組結果。 「地圖」功能如何知道要等到所有的承諾才能實現,直到自我完成呢? – LukeP

+0

@LukeP - 這就是藍鳥承諾所做的.map()。這只是通過迭代數組然後調用'Promise.all()'來收集承諾數組的快捷方式,它顯然會等待所有您傳遞的承諾,然後再解決它的主承諾。 [.map()'](http://bluebirdjs.com/docs/api/promise.map.html)的[bluebird doc]解釋得非常好。 – jfriend00