[Twisted-Python] why can't a callback be called with a deferred?

Glyph glyph at twistedmatrix.com
Wed Feb 20 23:55:24 MST 2019



> On Feb 19, 2019, at 5:34 AM, Chris Withers <chris at withers.org> wrote:
> 
> On 19/02/2019 11:41, Adi Roiban wrote:
>> 
>> I think it was introduced to catch some common bad usage patterns ...
>> like yours :)
> 
> Not a massively helpful comment.

I think what Adi was trying to get at here is that this is exactly the sort of type confusion that this assert was intended to defend against.

That said, the bare assert in question was definitely written with the implementor's sort of "this should never happen" hat on, not the "let's report a useful error to the user" hat.  So it could certainly stand to be improved regardless.

>> If you want to chain the deferreds, use the dedicated helper
>> https://twistedmatrix.com/documents/current/core/howto/defer.html#chaining-deferreds <https://twistedmatrix.com/documents/current/core/howto/defer.html#chaining-deferreds>

>> Deferred are not always 100% resolved/called.
>> You might have a deferred called, but the current result might be
>> another deferred... so it has no final result yet.
>> 
>> ----
>> 
>> so in your case, instead of `returnValue(result)` use
>> 
>> result = yield result
>> returnValue(result)
>> 
>> in this way, the result is resolved :)
> 
> The methods being hooked don't necessarily return deferreds.
> I'd like it to be an explicit choice of the caller, ie:
> 
> result = yield SomeProtocol.onMessage.called()
> # okay, we got here, we know onMessage was called,
> # now we might want to tick a clock, or otherwise simulate
> # async state manipulation.
> # now I want to make sure the deferred chain on the onMessage result has been completed:
> yield result

I'm not sure I understand your example here.  The assertion in question only happens if you call returnValue or do a return with a Deferred directly; this example doesn't do either of those things.

I think you could fix the linked example code to still do what you want by simply doing `returnValue(yield result)`?

-g
-------------- next part --------------
An HTML attachment was scrubbed...
URL: </pipermail/twisted-python/attachments/20190220/171a900a/attachment-0002.html>


More information about the Twisted-Python mailing list