Skip to content

Instantly share code, notes, and snippets.

@cefn
Created January 3, 2018 07:16
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save cefn/ead11ab8a744045440a01118fb299831 to your computer and use it in GitHub Desktop.
Save cefn/ead11ab8a744045440a01118fb299831 to your computer and use it in GitHub Desktop.
Properly cancelling scheduled asyncio tasks
import asyncio
import traceback
async def liver(lifeDelay):
try:
while True:
print("Living....la la la")
await asyncio.sleep(lifeDelay)
finally:
print("living() finished. Aaargh!")
async def killer(killDelay, coroToKill):
await asyncio.sleep(killDelay)
try:
print("Killing...")
# CancelledError will be raised by below call (uncaught in lifeFactory)
coroToKill.throw(asyncio.CancelledError)
except asyncio.CancelledError:
raise # if 'pass' is here then run_until_complete hangs
finally:
print("killer() finished")
def run():
loop = asyncio.get_event_loop()
lifeCoro = liver(0.5)
deathCoro = killer(2.0, lifeCoro)
coros = (lifeCoro, deathCoro)
try:
tasks = [loop.create_task(coro) for coro in coros]
gatheredTask = asyncio.gather(*tasks)
loop.run_until_complete(gatheredTask)
except asyncio.CancelledError:
try:
gatheredTask.cancel()
loop.run_until_complete(gatheredTask)
finally:
print("run() Finished")
while True:
try:
run()
except KeyboardInterrupt:
raise
except asyncio.CancelledError:
continue
except BaseException as e:
traceback.print_exc()
raise
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment