[Twisted-Python] Re: Making DeferredList look like Deferred
Lenny G Arbage
alengarbage at yahoo.com
Mon Feb 6 00:43:25 EST 2006
Jean-Paul Calderone exarkun at divmod.com
Fri Feb 3 14:08:54 MST 2006 wrote:
>
> ...However, if
> you pass a true value for fireOnOneErrback when
> constructing your DeferredList, any Deferred which
> errbacks will cause the DeferredList to errback; in
> this case it will never callback.
I think I must be missing something, but I can't
spot it. Here's the smallest example I've come up
with:
import random
from twisted.internet import reactor, defer
from twisted.python import failure
def error(err, msg):
print "failed: %s" % msg
reactor.stop()
def success(result, msg):
print "succeeded: %s" % msg
reactor.stop()
def defer2seconds(prob=0.5):
d = defer.Deferred()
if random.random() < prob:
print " deferred will succeed in 2s"
reactor.callLater(2, d.callback, True)
else:
print " deferred will fail in 2s"
reactor.callLater(2, d.errback, True)
return d
def deferlist2seconds(prob=0.25, num=2):
def itersuccess(result, i):
print " %i succeeded" % i
return result
def iterfail(err, i):
print " %i failed" % i
dlist = []
for i in range(num):
d = defer2seconds(prob)
d.addCallback(itersuccess, i)
d.addErrback(iterfail, i)
dlist.append(d)
dl = defer.DeferredList(dlist,
fireOnOneErrback=True)
return dl
def testdlist():
print "in testdlist"
#d = defer2seconds(prob=0.5)
d = deferlist2seconds(prob=0.5)
d.addCallback(success, "testdlist")
d.addErrback(error, "testdlist")
if __name__ == "__main__":
testdlist()
reactor.run()
The action here is really simple, with each deferred
randomly choosing to succeed or fail. The testdlist
function can call either the simple, single-deferred
test or the multi-deferredlist test. The goal here is
that the caller doesn't care what the underlying
function call does, in terms of Deferred v.
DeferredList. When calling the simple test, the
results are as expected:
in testdlist
deferred will fail in 2 seconds
failed: testdlist
in testdlist
deferred will succeed in 2 seconds
succeeded: testdlist
But when calling the DeferredList test, it never gets
into the DeferredList's errback.
in testdlist
deferred will succeed in 2 seconds
deferred will succeed in 2 seconds
0 succeeded
1 succeeded
succeeded: testdlist
in testdlist
deferred will fail in 2 seconds
deferred will succeed in 2 seconds
0 failed
1 succeeded
succeeded: testdlist
Why isn't the DeferredList's errback being called in
this case? It seems that no matter what I do (remove
the individual Deferreds' errbacks, change
fireOnOneErrback, etc), the DeferredList's callback
only is called. This doesn't sound like what you'd
expect. What am I doing wrong? What must I do to get
the DeferredList's errback to fire when any single
Deferred in the list has its errback called?
Tested using twisted 2.1.
Thanks,
Lenny
__________________________________________________
Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around
http://mail.yahoo.com
More information about the Twisted-Python
mailing list