我只是Tornado的新手而不是Python。
我正在尝试为CouchDB编写异步客户端(使用couchdb包)。
经过1天的研究/谷歌搜索,我发现每个帖子只是简单地使用HttpAsyncClient,而不是告诉为什么以及 gen.coroutine 如何工作。 源代码对我来说太复杂了解装饰器之后的装饰器HttpAsyncClient对我来说是一个不好的例子......
答案 0 :(得分:0)
坦率地说,对于ma来说,只有在阅读了源代码之后,我才能(部分地)理解逻辑
如果您使用somefunction()
装饰tornado.gen
:
yield somefunction()
中的tornado.coroutine.gen
。它会运行您的代码,直到yield
somefunction
another_callback()
” 。 somefunction()
执行的消失程度,Tornado维护了一个名为Runner
的特殊对象。它会记住阻止执行yield
的最后一个somefunction()
语句,并在执行装饰器gen
时首次运行。run()
方法返回并且装饰器退出,返回其自己的another_callback
。 Latter是由Tornado创建的一个特殊回调,很快就会发现,run()
与第3点时运行的Runner相同。新解决的Future已经产生了。 Runner使用.send()
方法将新解析的Future的值注入您的somefuncion
,这会导致ait被分配给函数中的变量(如果有),如同这样:
a = yield some_other_coroutine_for_example_async_client_fetch()
好的,这是一个要点,有很多deatails,其中一些我不得不包围我的头,尤其是异常处理,但HTH
答案 1 :(得分:0)
第一个答案涵盖了很多。我只是想让你知道一个更简单的抽象。 @ Gen.coroutine
res = yield foo()
协程的想法是异步执行foo()
,尤其是当foo需要大量的IO或网络工作时。
产量可能会激活foo()
执行并转移控制权,例如,呼叫者。它留下一个Runner来注册这个foo()
任务作为未来的obj。然后当foo()
成功返回结果时,这是神奇的事情,Runner将以yield语句执行结果的形式发回结果(告诉值yield和yield语句执行结果之间的差异)。