一旦任务完成,如何收集多个callback来调用

我似乎无法find一个通用的解决scheme,即使我觉得我不能成为第一个遇到这个问题。 我也怀疑这可能是我在这里采取了错误的方法。 让我知道。

我有一个Expressjs应用程序与各种API(主要是OAuth2)进行交互。 一旦请求进入应用程序检查是否有一个访问令牌从API获取数据。 万一令牌过期,它会请求一个新的。

现在,当我的应用程序同时收到第二个请求时,要求完全相同的API,我想避免再次调用访问令牌。

我所做的就是使用一个“收集器”,可以为给定的键存储callback。 存储callback的第一个请求获取一个回收器,一旦完成任务就调用callback器。 随后的所有callback都将被排队,并在稍后调用收集器callback。

这是简单的收集器类(CoffeeScript)

# Collect callbacks for tasks and execute all once the job is done module.exports = class Collector constructor: ()-> @tasks = {} add: (key, callback)-> unless @tasks[key] # Initiate callback list for the key with first callback @tasks[key] = [callback] return ()=> # Call all collected callbacks for the key (callback.apply {}, arguments for callback in @tasks[key]) # Reset callback list @tasks[key] = null else # Add callback to existing list @tasks[key].push callback return false 

我不确定在这个类中存储callback是否正确,但是使用数据库(Redis)我不得不find一种方法来存储callback。

一旦工作完成,是否有更好的方法来调用多个callback?

你为什么不把你的callback集合到一个循环的数组中,在原来的调用完成时执行每个包含的函数?

它可以像下面这样简单:

 var dones = []; dones.push(function (err, res) { console.log('hoo'); }); dones.push(function (err, res) { console.log('ray!'); }); function whenDone(err, res) { _.each(dones, function (done) { done(err, res); } }); } myWhateverFunction(whenDone); 

如果你想使它更漂亮,你可以把它包装成任何你想要的数据结构。

我没有针对你的问题的具体答案,但你应该检查出asynchronous模块。 我认为这是一个正确的方向: https : //github.com/caolan/async