I learn python asyncio and now struggling with Conditions. I wrote a simple code:
import asyncio
async def monitor(condition: asyncio.Condition):
current_task_name = asyncio.current_task().get_name()
print(f'Current task {current_task_name} started')
async with condition:
await condition.wait()
print(f'Condition lock released for task {current_task_name}, start doing smthg')
await asyncio.sleep(2)
print(f'Current task {current_task_name} finished')
async def setter(condition: asyncio.Condition):
print(f'Setter starts')
async with condition:
await asyncio.sleep(1)
condition.notify_all() # Пробуждаем все задачи
print('Setter finished')
print('Setter unlocked')
async def main():
cond = asyncio.Condition()
async with asyncio.TaskGroup() as tg:
tg.create_task(setter(cond))
[tg.create_task(monitor(cond)) for _ in range(3)]
# tg.create_task(setter(cond))
asyncio.run(main())
But the code catches a DeadLock after Setter unlocked
message. I cant realise why.
But if I swap task creation order in main
and create monitor tasks prior to creation setter task- all good.
please, I am a very new in asyncio, so please, in simple words...
I learn python asyncio and now struggling with Conditions. I wrote a simple code:
import asyncio
async def monitor(condition: asyncio.Condition):
current_task_name = asyncio.current_task().get_name()
print(f'Current task {current_task_name} started')
async with condition:
await condition.wait()
print(f'Condition lock released for task {current_task_name}, start doing smthg')
await asyncio.sleep(2)
print(f'Current task {current_task_name} finished')
async def setter(condition: asyncio.Condition):
print(f'Setter starts')
async with condition:
await asyncio.sleep(1)
condition.notify_all() # Пробуждаем все задачи
print('Setter finished')
print('Setter unlocked')
async def main():
cond = asyncio.Condition()
async with asyncio.TaskGroup() as tg:
tg.create_task(setter(cond))
[tg.create_task(monitor(cond)) for _ in range(3)]
# tg.create_task(setter(cond))
asyncio.run(main())
But the code catches a DeadLock after Setter unlocked
message. I cant realise why.
But if I swap task creation order in main
and create monitor tasks prior to creation setter task- all good.
please, I am a very new in asyncio, so please, in simple words...
Share Improve this question asked Mar 27 at 11:09 IzaeDAIzaeDA 3856 bronze badges1 Answer
Reset to default 3In your original code, the setter
task is started before the monitor
tasks. When setter
calls notify_all()
, no monitor tasks are yet waiting so no tasks are notified. Later, the monitors reach condition.wait()
but remain stuck because no further notifications are sent.
When you reverse the order, starting monitor
tasks first, they begin waiting on the condition before the setter
notifies. As a result, they are properly awakened and the deadlock is avoided.
To fix the issue, ensure that all tasks that should wait on the condition are created and running before calling notify_all()
.