我正在编写一个框架,该框架将调用用户提供的函数。
我想允许使用的提供的函数是以下任何一个:
- 一个简单的函数
- 一个函数返回
asyncio.Future
- 一个
asyncio.coroutine
即用户函数可以是同步的也可以是异步的,框架事先不知道,但需要应对所有变体。
扭曲 has defer.maybeDeferred
为此。 asyncio
的方式是什么?
我有如下内容(完整代码 here ):
import types
types.GeneratorType
def maybe_async(value):
if isinstance(value, types.GeneratorType) or \
isinstance(value, asyncio.futures.Future):
return value
else:
future = asyncio.Future()
future.set_result(value)
return future
然后在框架中像这样调用用户提供的函数f
:
res = yield from maybe_async(f(x))
这会将任何普通函数返回值包装到 Future
- always。我对此的性能或其他影响持谨慎态度。
上面是“推荐”方式吗?
另外,"inline" version of above code没有这个开销。我如何才能兼顾两者的优点:“普通”情况没有开销,但整个框架都没有用于检查异步返回的代码重复?
总而言之,似乎有两个(主要)选项:
习语一:
res = f(x)
if yields(res):
res = yield from res
在哪里
def yields(value):
return isinstance(value, asyncio.futures.Future) or inspect.isgenerator(value)
或
成语2:
res = yield from asyncio.coroutine(f)(x)
我是一名优秀的程序员,十分优秀!