We write a simple code:
import asyncio from datetime import datetime from functools import partial handle = [None] async def callback(): print(datetime.now()) handle[0] = asyncio.get_event_loop().call_later( 10, partial(asyncio.ensure_future, callback())) def main(): try: handle[0] = asyncio.ensure_future(callback()) asyncio.get_event_loop().run_forever() except KeyboardInterrupt: pass if __name__ == '__main__': main()
Run and after ~ 15 seconds. remove via Ctrl + C
$ ./period.py 2016-09-09 14:08:05.392415 2016-09-09 14:08:10.393921 ^Csys:1: RuntimeWarning: coroutine 'callback' was never awaited
RuntimeWarning hints that the output is not entirely correct. How to complete correctly?
The solution was found: you need to replace the partial
on lambda
. The error was due to the fact that when calling callback()
a coroutine was created, which was not tied anywhere. Thus, the correct code will be as follows:
import asyncio from datetime import datetime from functools import partial handle = [None] async def callback(): print(datetime.now()) handle[0] = asyncio.get_event_loop().call_later( 10, lambda: asyncio.ensure_future(callback())) loop.stop() def main(): try: handle[0] = asyncio.ensure_future(callback()) asyncio.get_event_loop().run_forever() except KeyboardInterrupt: pass finally: handle[0].cancel() loop.close() if __name__ == '__main__': main()
loop.stop()
- tonal call at the end of thecallback()
functionpartial(asyncio.ensure_future, callback())
If you replace it withlambda: asyncio.ensure_future(callback())
everything ends correctly. And it comes from the fact that the callback () call generates a coroutine that no one expected, and when it ended, they lost it. - tonal