【问题标题】:How do I attach two separate callbacks to a Twisted deferred, so both fire after the result is ready?如何将两个单独的回调附加到 Twisted deferred,以便在结果准备好后都触发?
【发布时间】:2014-06-05 04:41:52
【问题描述】:

我对 Twisted 不是很有经验,但这是我目前所了解的。
当我进行数据库查询时,例如:

db = database.veryLongQuery(sql, binds)

我可以添加回调来处理结果,

db.addCallback(lambda res: dispalyResult(res))

否则如果我需要对同一个结果做多件事,我可以做一个方法:

def doTwoThings(self, res):
    self.d1 = anotherDeferred(res) # write to table A, return lastRowId
    self.d2 = yetAnotherDeferred(res) # write to table B, return lastRowId
    return d1

并将其附加到db(作为第一个回调)

db.addCallback(self.doTwoThings)

但是,我想从一开始就在创建数据库的同时引用d1d2,因为会发生其他事件,我需要向@987654328 添加回调@ 和d2

我将如何将两个(或更多)单独的回调链附加到同一个延迟 db 上,以便它“拆分”,并且一旦结果准备好,两者都会并排触发?

这样我可以从一开始就跟踪每个延迟并在必要时访问它们。

或者,有没有办法从一开始就创建 d1d2,所以我可以访问这些名称?

【问题讨论】:

  • 总是有可能只有一个自定义回调函数,除了调用其他两个函数之外什么都不做。我无法真正说出您要做什么并且不了解您的环境,但是我知道的任何承诺/延迟功能都可以让您拥有尽可能多的完成处理程序。
  • 基本上我正在使用代理(行 ID)主键写入数据库。当我也想写入数据库的其他事件到达时,我必须等待原始写入完成并返回行 ID/键,因为那将是外键。

标签: python-2.7 twisted deferred


【解决方案1】:

你可以这样使用:

def splitResults(d1, d2):
    def splitter(val):
        # Pass val to d2 chain
        d2.callback(val)
        # Return val into d1's chain
        return val

    def splitterError(err):
        d2.errback(err)
    d1.addCallbacks(splitter, splitterError)

所以,每当 d1 得到结果时,它也会将它传递给 d2。

【讨论】:

  • 这是实现的一部分。不过,您忘记了错误处理。
  • 谢谢,这行得通。对于错误处理,将 errbacks 添加到 d1 和 d2 是否足够?当 val 失败时,它只会将失败返回到下一个回调。
猜你喜欢
  • 1970-01-01
  • 2016-03-07
  • 1970-01-01
  • 2010-10-08
  • 2016-05-28
  • 2018-12-03
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多