6

我有一些使用tornadogen.coroutine的异步函数,我通常将它们用作基于 tornado 的 Web 应用程序的一部分。但是,我想从一个普通的旧 python 脚本中调用其中一些来执行一些管理任务。我该怎么做呢?

from tornado import gen

import some_internal_stuff

@gen.coroutine
def myfunc(x):
    y = yield some_internal_stuff.another_async_func(x)
    raise gen.Return(y)

if __name__ == "__main__":
    # What do I put here to call myfunc(1) and get the async return value?
    pass

更新:

一个更具体的例子:

from tornado import gen

@gen.coroutine
def another_async_func(x):
    print "aaf"
    raise gen.Return(x + 1)

@gen.coroutine
def myfunc(x):
    print "myfunc"
    y = yield another_async_func(x)
    print "back"
    raise gen.Return(y)

def callback(y):
    print "Callback called with %d" % y

if __name__ == "__main__":
    myfunc(1, callback=callback)

运行此输出:

myfunc
aaf
4

2 回答 2

18

有一个内置方法可以运行单个调用然后停止循环,因此只要在 PYTHONPATH 中有龙卷风,只需将事件循环添加到普通的 python 脚本就很简单了run_syncIOLoop

用具体的例子:

from tornado import gen, ioloop

@gen.coroutine
def another_async_func(x):
    print "aaf"
    raise gen.Return(x + 1)

@gen.coroutine
def myfunc(x):
    print "myfunc"
    y = yield another_async_func(x)
    print "back"
    raise gen.Return(y)

@gen.coroutine
def main():
    y = yield myfunc(1)
    print "Callback called with %d" % y

if __name__ == "__main__":
    ioloop.IOLoop.instance().run_sync(main)

这输出:

myfunc
aaf
back
Callback called with 2

注意run_sync嵌套不好;如果您在同一调用run_sync的函数中调用,则内部调用的完成将停止,并且内部调用将返回之后不再有s。run_syncIOLoopIOLoopyield

于 2013-10-30T23:21:38.487 回答
1

这是另一种可能性,使用线程,这取决于问题的复杂性和您的需求:

if __name__ == "__main__":
    import threading, time
    # The tornado IO loop doesn't need to be started in the main thread
    # so let's start it in another thread:
    t = threading.Thread(target=IOLoop.instance().start)
    t.daemon = True
    t.start()

    myfunc(1, callback=callback)
    # now the main loop needs wait; you can do that by polling a value, sleeping,
    # or waiting on a lock. I've chosen to sleep here, but a lock is probably more
    # appropriate; and, once computation is done, release the lock.
    time.sleep(2)
于 2013-10-30T23:25:35.457 回答