我有以下简单的脚本:
#!/usr/bin/env python
from twisted.internet import defer
from twisted.web.client import getPage, reactor
def success(results):
print 'success'
def error(results):
print 'error'
def finished(results):
print 'finished', results
tasks = []
d = getPage('thiswontwork').addCallback(success).addErrback(error)
tasks.append(d)
dl = defer.DeferredList(tasks)
dl.addCallback(finished)
reactor.run()
产生以下输出:
error
finished [(True, None)]
我希望这个错误任务返回false,因为getPages任务失败并调用它的错误回调。任何人都可以解释这种行为吗?
答案 0 :(得分:4)
让我添加一个超出您选择答案的想法:
在您的问题中,您打印了调用延迟(列表)回调(finished
)的参数,并且您注意到您希望它是false
(因为之前发生的错误)
这种期望表明你对延迟的思考会让你感到困惑later。
让我看看我能否打破这一点......
(这里有很多细节和巧妙的东西,我会尽我所能)
延期是:
callback
和errback
函数回调
addCallbacks
(注意其复数形式)允许您一次添加回调和错误回复addCallback
添加一个回调(并将errback设置为跳转到队列中的下一个条目)addErrback
添加了一个errback(并设置回调以跳转到队列中的下一个条目)addBoth
添加一个函数作为errback和回调(...这意味着它需要弄清楚为什么通过arg调用它被调用从krondo's part 7绘图:( ...扭曲的文档也有good drawing)
如果将某个函数添加到延迟为callback
且延迟已达到其“触发”的点。在此之前的步骤成功返回,延迟时将上一个成功函数的返回值传递给callback
中定义的函数。
如果将某个函数添加到延迟为errback
且延迟已达到其“触发”的点。上一步返回Failure
对象(或引发异常,将其转换为Failure
对象),然后将使用该errback
对象调用Failure
。 注意! 如果errback没有返回Failure
,则延迟将转回调用callback
链,不是错误!
从Krondo's part 9绘制:
虽然这可能看起来像是一个让人烦恼的事情,但是它可以让你实现像延迟错误恢复这样的事情,这可能真的很有用(而且在协议设计中并非罕见)
I.E :(来自Krondo's part 9):
把这一切都放在一起,你想到的错误就是"我希望这个错误任务能够返回错误的"是finished
不被任何类型的错误任务调用,它被延迟调用,并且它只调用成功(因为它仅作为callback
加载到errback
而不是finished
)
如果您已将errback
功能同时加载为callback
和addBoth
(可能是通过Failure
),并且您已按照回答建议转发回复通过返回finished
对象的错误的状态,您的False
函数在技术上仍然无法通过 Failure
!它会收到一个{{1}}对象。
......就像我说的那样,在这个东西中有很多巧妙的......
如果你发现任何这些有用(......或者即使你不是 - 我不是作家的好人),你真的应该挖掘Krondo's twisted introduction。我认为在完成该指南后,你会发现很多这些快照成为焦点。
答案 1 :(得分:3)
如果您没有从errback
返回错误/异常,则认为该错误已被处理。尝试更改error()
功能:
def error(results):
print 'error'
return results
这样会返回错误(results
),然后DeferredList
会看到错误并调用errback
。