我无法理解这个问题如何将动态结果添加到承诺链中,如果可能的话,我可以随处查看。希望有人可以澄清或给我一个很好的解决方案,以便我试图完成以下示例(它是一个小型音乐播放器):
// API requests are done with a promise
let pfetch = (url) => Promise.resolve( $.ajax(...) )
// This will give me all playlists from a user
pfetch( 'USER-API-URL' )
// The playlists i get have tracklists
.then( results =>
// When all playlists are fetched continue (Promise.all = parallel)
Promise.all( results.playlists.map( playlist => pfetch(playlist.url) ) )
)
// Results of all playlists in arguments
.then( playlists =>
// Each playlist has tracks and next_url
playlists.map( playlist => {
/* playlist.tracks
* if (playlist.next_url) pfetch(playlist.next_url)
* append results to playlist.tracks
*/
})
)
//only continue if all all tracks are complete
//can i do a Promise.join() in the previous step?
.then( () => console.log('finished,yay!') )
某些曲目列表的响应中有next_url
,这意味着我还应该获取属于曲目列表的下一个网址,这样我就可以获得完整的tracklist.tracks
。但是,这必须是顺序的,因为我不知道响应中是否有后续的next_url
。如果没有next_url
我完成了一个曲目列表,并且可以对下一个曲目列表执行相同的操作(因此.map
)。
所以我的问题,你如何在承诺中进行动态内容链接?我知道您可以使用reduce
进行排序,但在这种情况下,next_url
的数量并不固定。我已经考虑了递归,但还没有找到Promise.each
的好例子。
提前竖起大拇指。
答案 0 :(得分:1)
如果您创建一个递归处理播放列表网址的函数
var getPlaylistUrl = url =>
pfetch(url).then(playlist =>
playlist.next_url ? Promise.all([].concat.apply([playlist.tracks], getPlaylistUrl(playlist.next_url))) : playlist.tracks
);
您应该能够按如下方式重写代码
pfetch('USER-API-URL')
.then(results => Promise.all(results.playlists.map(playlist => getPlaylistUrl(playlist.url))))
.then( playlists => {
// playlists should be complete
})
.then( () => console.log('finished,yay!') );