#python #async-await #python-asyncio
Вопрос:
Весь мой код написан без учета asyncio; однако я использую одну асинхронную функцию (написанную другим разработчиком; для моих целей это черный ящик). Давайте назовем это func_1
. Мне нужно вызвать эту функцию изнутри другой функции, вызвать ее func_2
(которая сама по себе может быть вызвана в произвольно длинной цепочке функций func_3
и func_4
т. Д.).
Поскольку func_1
это асинхронно, мне нужно его дождаться, но так как я его вызываю func_2
, мне также нужно выполнить func_2
асинхронность (я не могу ждать в несинхронной функции). И это продолжается; мне нужно превратить всю цепочку функций func_2
func_3
func_4
в асинхронные функции.
Есть ли способ избежать этого? Я просто хочу позвонить func_1
, дождаться его завершения и использовать результаты в остальной части моего обычного кода на python. Могу ли я создать оболочку, func_1
чтобы разрешить это?
То, что я хочу, по сути, заключается в следующем, что не работает:
# This is the function defined by someone else
async def func_1(*args):
return something(*args)
# This is my wrapper
def func_1_wrapper(*args):
return await func_1(*args)
# So that I can call it like normal within the rest of my code
def func_2(*args):
# do something
a = func_1_wrapper(*args)
# do something else
Комментарии:
1. Вы можете выполнить
func_1
входfunc_1_wrapper
и дождаться его завершения с помощьюasyncio.run
:asyncio.run(func_1())
2. Если вы заботитесь о том, чтобы он был асинхронным, потому что он позволяет (псевдо) параллельное выполнение кода , тогда да, вам нужно сделать все
await
иasync
полностью. Если нет, и вы не противfunc_1
заблокировать все, пока это не будет сделано, простоasyncio.run(func_1())
.3. Верно, звучит намного проще, чем я ожидал. Единственное, чего у меня нет
asyncio.run
в моей версии пакета. Кстати , у моегоasyncio
нетasyncio.__version__
, что меня удивляет.run_coroutine_threadsafe
Сделал бы то же самое?4. В более старых версиях вы бы использовали
asyncio.get_event_loop().run_until_complete(func_1())
.5. Я предполагаю , что в стандартных библиотечных пакетах нет
__version__
, я об этом не знал. Так что это похоже на python 3.6.5.