As mentioned before, asyncio
runs on a single thread. All asyncio.Future objects and coroutines are managed by this single event loop within that single thread. There’s no inherent need for them to be internally thread-safe because there’s only one thread actively operating on them at any given moment.
NOTE
Yep, so if you just use
asyncio
itself without any other ‘multi-thread/process’ magic, things should just work.
If you do try to call methods on an asyncio.Future
(like set_result()
or cancel()
) from a different thread than the one running the asyncio event loop, you could introduce race conditions, as asyncio.Future
doesn’t have internal locks to protect its state from simultaneous modification by an external thread.
NOTE
So, that is to say, the internal states of
asyncio.Future
is not really thread safe. So if two threads accessing the sameasyncio.Future
simultaneously, bad thing can happen.Yep, that sounds reasonable.
The correct way to interact with an asyncio.Future
from another thread is to use loop.call_soon_threadsafe()
. This method specifically queues a callable to be run on the event loop’s thread, ensuring that the interaction with the asyncio.Future
happens in a thread-safe manner (by being executed on the main event loop thread).