【发布时间】:2013-11-19 22:02:10
【问题描述】:
我正在构建一个 node.js 应用程序,并且正在评估 Sequelize.js 的持久性对象。我需要做的一件事是在修改对象时发布新值。最明智的做法似乎是使用 afterUpdate 挂钩。
它几乎可以完美运行,但是当我保存一个对象时,钩子会传递已保存对象的所有值。通常这是可取的,但为了减少发布/订阅的喋喋不休,我宁愿不重新发布未保存的字段。
例如,运行以下命令
tasks[0].updateAttributes({assignee: 10}, ['assignee']);
将自动在适当的频道上为该任务的受让人发布新值,但不会重新发布任何其他字段,这没有改变。
我最接近的是 afterUpdate 钩子:
Task.hook('afterUpdate', function(task, fn) {
Object.keys(task).forEach(function publishValue(key) {
pubSub.publish('Task:'+task.id+'#'+key, task[key]);
});
return fn();
});
这很简单,但是由于“任务”对象具有所有字段,因此我会产生不必要的噪音。 (pubSub 系统不知道以前的值,我想保持这种状态。)
我可以覆盖任务对象(以及我的所有其他对象)中的设置器,但我不希望在保存对象之前发布。要保存的对象似乎没有旧值(我可以找到),所以我不能以此为基础发布。
到目前为止,从设计的角度来看,我想出的最佳答案是调整 dao.js 的一行以将保存的值添加到返回的对象中,并在挂钩中使用它:
self.__factory.runHooks('after' + hook, _.extend({}, result.values, {savedVals: args[2]} ), function(err, newValues) {
Task.hook('afterUpdate', function(task, fn) {
Object.keys(task.savedVals).forEach(function publishValue(key) {
pubSub.publish('Task:'+task.id+'#'+key, task[key]);
});
return fn();
});
从维护的角度来看,更改 Sequelize 库显然并不理想。
所以我的问题是双重的:有没有更好的方法可以在不修改 dao.js 的情况下将所需的信息传递给我的钩子,或者有更好的方法来解决我的基本需求?
提前致谢!
【问题讨论】:
-
我认为这实际上是一个真正有效的钩子用例 - 请提交 PR 并附上您的更改 :)
-
当我向我的应用程序添加验证时,我正准备输入拉取请求,但事情发生了 - 正如上面所写,savedVals 在验证时被添加,然后保存失败。我将不得不再考虑一段时间。
-
...我刚输入,就看到了明显的答案。修改问题,继续 PR。
标签: javascript node.js sequelize.js