blob: 18da18873dbfb5577888944b7eacf84854553cb5 [file] [log] [blame]
R David Murray6a143812013-12-20 14:37:39 -05001.. currentmodule:: asyncio
Yury Selivanov8be876e2018-09-11 17:10:37 -07002
Victor Stinner606ab032014-02-01 03:18:58 +01003.. _asyncio-sync:
Victor Stinnerea3183f2013-12-03 01:08:00 +01004
Yury Selivanov8be876e2018-09-11 17:10:37 -07005==========================
6Synchronization Primitives
Victor Stinnerea3183f2013-12-03 01:08:00 +01007==========================
8
Yury Selivanov8be876e2018-09-11 17:10:37 -07009asyncio synchronization primitives are designed to be similar to
10those of the :mod:`threading` module with two important caveats:
lf627d2c82017-07-25 17:03:51 -060011
Yury Selivanov8be876e2018-09-11 17:10:37 -070012* asyncio primitives are not thread-safe, therefore they should not
Elvis Pranskevichus1fa2ec42018-09-17 19:16:44 -040013 be used for OS thread synchronization (use :mod:`threading` for
Yury Selivanov8be876e2018-09-11 17:10:37 -070014 that);
15
Elvis Pranskevichus1fa2ec42018-09-17 19:16:44 -040016* methods of these synchronization primitives do not accept the *timeout*
Yury Selivanov8be876e2018-09-11 17:10:37 -070017 argument; use the :func:`asyncio.wait_for` function to perform
18 operations with timeouts.
19
Carol Willing4e824e92018-09-13 18:28:19 -070020asyncio has the following basic sychronization primitives:
Victor Stinner7a55b882015-01-30 00:37:04 +010021
22* :class:`Lock`
23* :class:`Event`
24* :class:`Condition`
25* :class:`Semaphore`
26* :class:`BoundedSemaphore`
27
Yury Selivanov8be876e2018-09-11 17:10:37 -070028
29---------
Victor Stinner7a55b882015-01-30 00:37:04 +010030
Victor Stinnerea3183f2013-12-03 01:08:00 +010031
Victor Stinner8c462c52014-01-24 18:11:43 +010032Lock
Yury Selivanov8be876e2018-09-11 17:10:37 -070033====
Victor Stinner8c462c52014-01-24 18:11:43 +010034
Victor Stinnerea3183f2013-12-03 01:08:00 +010035.. class:: Lock(\*, loop=None)
36
Yury Selivanov8be876e2018-09-11 17:10:37 -070037 Implements a mutex lock for asyncio tasks. Not thread-safe.
Victor Stinnerea3183f2013-12-03 01:08:00 +010038
Yury Selivanov8be876e2018-09-11 17:10:37 -070039 An asyncio lock can be used to guarantee exclusive access to a
40 shared resource.
Victor Stinnerea3183f2013-12-03 01:08:00 +010041
Yury Selivanov8be876e2018-09-11 17:10:37 -070042 The preferred way to use a Lock is an :keyword:`async with`
43 statement::
Victor Stinnerea3183f2013-12-03 01:08:00 +010044
Yury Selivanov8be876e2018-09-11 17:10:37 -070045 lock = asyncio.Lock()
Victor Stinnerea3183f2013-12-03 01:08:00 +010046
Yury Selivanov8be876e2018-09-11 17:10:37 -070047 # ... later
48 async with lock:
49 # access shared state
Victor Stinnerea3183f2013-12-03 01:08:00 +010050
Yury Selivanov8be876e2018-09-11 17:10:37 -070051 which is equivalent to::
Victor Stinnerea3183f2013-12-03 01:08:00 +010052
Yury Selivanov8be876e2018-09-11 17:10:37 -070053 lock = asyncio.Lock()
Victor Stinner7b2c3c62015-02-26 10:39:16 +010054
Yury Selivanov8be876e2018-09-11 17:10:37 -070055 # ... later
56 await lock.acquire()
57 try:
58 # access shared state
59 finally:
60 lock.release()
Victor Stinnerea3183f2013-12-03 01:08:00 +010061
Victor Stinnerbdd574d2015-02-12 22:49:18 +010062 .. coroutinemethod:: acquire()
Victor Stinnerea3183f2013-12-03 01:08:00 +010063
Yury Selivanov8be876e2018-09-11 17:10:37 -070064 Acquire the lock.
Victor Stinnerea3183f2013-12-03 01:08:00 +010065
Yury Selivanov8be876e2018-09-11 17:10:37 -070066 This method waits until the lock is *unlocked*, sets it to
67 *locked* and returns ``True``.
Victor Stinnerea3183f2013-12-03 01:08:00 +010068
69 .. method:: release()
70
Yury Selivanov8be876e2018-09-11 17:10:37 -070071 Release the lock.
Victor Stinnerea3183f2013-12-03 01:08:00 +010072
Yury Selivanov8be876e2018-09-11 17:10:37 -070073 When the lock is *locked*, reset it to *unlocked* and return.
Victor Stinnerea3183f2013-12-03 01:08:00 +010074
Carol Willing4e824e92018-09-13 18:28:19 -070075 If the lock is *unlocked*, a :exc:`RuntimeError` is raised.
Victor Stinnerea3183f2013-12-03 01:08:00 +010076
Yury Selivanov8be876e2018-09-11 17:10:37 -070077 .. method:: locked()
78
79 Return ``True`` if the lock is *locked*.
Victor Stinnerea3183f2013-12-03 01:08:00 +010080
81
Victor Stinner8c462c52014-01-24 18:11:43 +010082Event
Yury Selivanov8be876e2018-09-11 17:10:37 -070083=====
Victor Stinner8c462c52014-01-24 18:11:43 +010084
Victor Stinnerea3183f2013-12-03 01:08:00 +010085.. class:: Event(\*, loop=None)
86
Yury Selivanov8be876e2018-09-11 17:10:37 -070087 An event object. Not thread-safe.
Victor Stinnerea3183f2013-12-03 01:08:00 +010088
Yury Selivanov8be876e2018-09-11 17:10:37 -070089 An asyncio event can be used to notify multiple asyncio tasks
90 that some event has happened.
Victor Stinnerea3183f2013-12-03 01:08:00 +010091
Yury Selivanov8be876e2018-09-11 17:10:37 -070092 An Event object manages an internal flag that can be set to *true*
93 with the :meth:`set` method and reset to *false* with the
94 :meth:`clear` method. The :meth:`wait` method blocks until the
95 flag is set to *true*. The flag is set to *false* initially.
Victor Stinner7b2c3c62015-02-26 10:39:16 +010096
Yury Selivanov7372c3b2018-09-14 15:11:24 -070097 .. _asyncio_example_sync_event:
98
Yury Selivanov8be876e2018-09-11 17:10:37 -070099 Example::
Victor Stinnerea3183f2013-12-03 01:08:00 +0100100
Yury Selivanov8be876e2018-09-11 17:10:37 -0700101 async def waiter(event):
Carol Willing4e824e92018-09-13 18:28:19 -0700102 print('waiting for it ...')
Yury Selivanov8be876e2018-09-11 17:10:37 -0700103 await event.wait()
104 print('... got it!')
Victor Stinnerea3183f2013-12-03 01:08:00 +0100105
Yury Selivanov8be876e2018-09-11 17:10:37 -0700106 async def main():
107 # Create an Event object.
108 event = asyncio.Event()
Victor Stinnerea3183f2013-12-03 01:08:00 +0100109
Yury Selivanov8be876e2018-09-11 17:10:37 -0700110 # Spawn a Task to wait until 'event' is set.
111 waiter_task = asyncio.create_task(waiter(event))
Victor Stinnerea3183f2013-12-03 01:08:00 +0100112
Yury Selivanov8be876e2018-09-11 17:10:37 -0700113 # Sleep for 1 second and set the event.
114 await asyncio.sleep(1)
115 event.set()
Victor Stinnerea3183f2013-12-03 01:08:00 +0100116
Yury Selivanov8be876e2018-09-11 17:10:37 -0700117 # Wait until the waiter task is finished.
118 await waiter_task
119
120 asyncio.run(main())
Victor Stinnerea3183f2013-12-03 01:08:00 +0100121
Victor Stinnerbdd574d2015-02-12 22:49:18 +0100122 .. coroutinemethod:: wait()
Victor Stinnerea3183f2013-12-03 01:08:00 +0100123
Yury Selivanov8be876e2018-09-11 17:10:37 -0700124 Wait until the event is set.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100125
Yury Selivanov8be876e2018-09-11 17:10:37 -0700126 If the event is set, return ``True`` immediately.
127 Otherwise block until another task calls :meth:`set`.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100128
Yury Selivanov8be876e2018-09-11 17:10:37 -0700129 .. method:: set()
130
131 Set the event.
132
133 All tasks waiting for event to be set will be immediately
134 awakened.
135
136 .. method:: clear()
137
138 Clear (unset) the event.
139
140 Tasks awaiting on :meth:`wait` will now block until the
141 :meth:`set` method is called again.
142
143 .. method:: is_set()
144
145 Return ``True`` if the event is set.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100146
147
Victor Stinner8c462c52014-01-24 18:11:43 +0100148Condition
Yury Selivanov8be876e2018-09-11 17:10:37 -0700149=========
Victor Stinner8c462c52014-01-24 18:11:43 +0100150
Andrew Svetlovf200ce62014-07-26 19:50:37 +0300151.. class:: Condition(lock=None, \*, loop=None)
Victor Stinnerea3183f2013-12-03 01:08:00 +0100152
Yury Selivanov8be876e2018-09-11 17:10:37 -0700153 A Condition object. Not thread-safe.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100154
Yury Selivanov8be876e2018-09-11 17:10:37 -0700155 An asyncio condition primitive can be used by a task to wait for
Elvis Pranskevichus1fa2ec42018-09-17 19:16:44 -0400156 some event to happen and then get exclusive access to a shared
Yury Selivanov8be876e2018-09-11 17:10:37 -0700157 resource.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100158
Yury Selivanov8be876e2018-09-11 17:10:37 -0700159 In essence, a Condition object combines the functionality
Elvis Pranskevichus1fa2ec42018-09-17 19:16:44 -0400160 of an :class:`Event` and a :class:`Lock`. It is possible to have
161 multiple Condition objects share one Lock, which allows coordinating
Yury Selivanov8be876e2018-09-11 17:10:37 -0700162 exclusive access to a shared resource between different tasks
163 interested in particular states of that shared resource.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100164
Yury Selivanov8be876e2018-09-11 17:10:37 -0700165 The optional *lock* argument must be a :class:`Lock` object or
166 ``None``. In the latter case a new Lock object is created
167 automatically.
Andrew Svetlov28d8d142017-12-09 20:00:05 +0200168
Yury Selivanov8be876e2018-09-11 17:10:37 -0700169 The preferred way to use a Condition is an :keyword:`async with`
170 statement::
171
172 cond = asyncio.Condition()
173
174 # ... later
175 async with cond:
176 await cond.wait()
177
178 which is equivalent to::
179
180 cond = asyncio.Condition()
181
182 # ... later
Kevin Mai-Husan Chiad73ac0e2019-02-14 10:39:25 +0800183 await cond.acquire()
Yury Selivanov8be876e2018-09-11 17:10:37 -0700184 try:
185 await cond.wait()
186 finally:
Kevin Mai-Husan Chiad73ac0e2019-02-14 10:39:25 +0800187 cond.release()
Victor Stinner7b2c3c62015-02-26 10:39:16 +0100188
Victor Stinnerbdd574d2015-02-12 22:49:18 +0100189 .. coroutinemethod:: acquire()
Larry Hastings3732ed22014-03-15 21:13:56 -0700190
191 Acquire the underlying lock.
192
Yury Selivanov8be876e2018-09-11 17:10:37 -0700193 This method waits until the underlying lock is *unlocked*,
194 sets it to *locked* and returns ``True``.
Larry Hastings3732ed22014-03-15 21:13:56 -0700195
Victor Stinnerea3183f2013-12-03 01:08:00 +0100196 .. method:: notify(n=1)
197
Yury Selivanov8be876e2018-09-11 17:10:37 -0700198 Wake up at most *n* tasks (1 by default) waiting on this
199 condition. The method is no-op if no tasks are waiting.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100200
Yury Selivanov8be876e2018-09-11 17:10:37 -0700201 The lock must be acquired before this method is called and
202 released shortly after. If called with an *unlocked* lock
203 a :exc:`RuntimeError` error is raised.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100204
Larry Hastings3732ed22014-03-15 21:13:56 -0700205 .. method:: locked()
206
207 Return ``True`` if the underlying lock is acquired.
208
Victor Stinnerea3183f2013-12-03 01:08:00 +0100209 .. method:: notify_all()
210
Yury Selivanov8be876e2018-09-11 17:10:37 -0700211 Wake up all tasks waiting on this condition.
212
213 This method acts like :meth:`notify`, but wakes up all waiting
214 tasks.
215
216 The lock must be acquired before this method is called and
217 released shortly after. If called with an *unlocked* lock
218 a :exc:`RuntimeError` error is raised.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100219
Larry Hastings3732ed22014-03-15 21:13:56 -0700220 .. method:: release()
221
222 Release the underlying lock.
223
Yury Selivanov8be876e2018-09-11 17:10:37 -0700224 When invoked on an unlocked lock, a :exc:`RuntimeError` is
225 raised.
Larry Hastings3732ed22014-03-15 21:13:56 -0700226
Victor Stinnerbdd574d2015-02-12 22:49:18 +0100227 .. coroutinemethod:: wait()
Victor Stinnerea3183f2013-12-03 01:08:00 +0100228
229 Wait until notified.
230
Yury Selivanov8be876e2018-09-11 17:10:37 -0700231 If the calling task has not acquired the lock when this method is
Victor Stinnerea3183f2013-12-03 01:08:00 +0100232 called, a :exc:`RuntimeError` is raised.
233
Yury Selivanov8be876e2018-09-11 17:10:37 -0700234 This method releases the underlying lock, and then blocks until
235 it is awakened by a :meth:`notify` or :meth:`notify_all` call.
236 Once awakened, the Condition re-acquires its lock and this method
237 returns ``True``.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100238
Victor Stinnerbdd574d2015-02-12 22:49:18 +0100239 .. coroutinemethod:: wait_for(predicate)
Victor Stinnerea3183f2013-12-03 01:08:00 +0100240
Yury Selivanov8be876e2018-09-11 17:10:37 -0700241 Wait until a predicate becomes *true*.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100242
Yury Selivanov8be876e2018-09-11 17:10:37 -0700243 The predicate must be a callable which result will be
244 interpreted as a boolean value. The final value is the
245 return value.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100246
247
Victor Stinner8c462c52014-01-24 18:11:43 +0100248Semaphore
Yury Selivanov8be876e2018-09-11 17:10:37 -0700249=========
Victor Stinner8c462c52014-01-24 18:11:43 +0100250
Victor Stinnerea3183f2013-12-03 01:08:00 +0100251.. class:: Semaphore(value=1, \*, loop=None)
252
Yury Selivanov8be876e2018-09-11 17:10:37 -0700253 A Semaphore object. Not thread-safe.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100254
255 A semaphore manages an internal counter which is decremented by each
Yury Selivanov8be876e2018-09-11 17:10:37 -0700256 :meth:`acquire` call and incremented by each :meth:`release` call.
257 The counter can never go below zero; when :meth:`acquire` finds
258 that it is zero, it blocks, waiting until some task calls
259 :meth:`release`.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100260
Yury Selivanov8be876e2018-09-11 17:10:37 -0700261 The optional *value* argument gives the initial value for the
262 internal counter (``1`` by default). If the given value is
263 less than ``0`` a :exc:`ValueError` is raised.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100264
Yury Selivanov8be876e2018-09-11 17:10:37 -0700265 The preferred way to use a Semaphore is an :keyword:`async with`
266 statement::
Andrew Svetlov28d8d142017-12-09 20:00:05 +0200267
Yury Selivanov8be876e2018-09-11 17:10:37 -0700268 sem = asyncio.Semaphore(10)
269
270 # ... later
271 async with sem:
272 # work with shared resource
273
274 which is equivalent to::
275
276 sem = asyncio.Semaphore(10)
277
278 # ... later
279 await sem.acquire()
280 try:
281 # work with shared resource
282 finally:
283 sem.release()
Victor Stinner7b2c3c62015-02-26 10:39:16 +0100284
Victor Stinnerbdd574d2015-02-12 22:49:18 +0100285 .. coroutinemethod:: acquire()
Victor Stinnerea3183f2013-12-03 01:08:00 +0100286
287 Acquire a semaphore.
288
Yury Selivanov8be876e2018-09-11 17:10:37 -0700289 If the internal counter is greater than zero, decrement
Elvis Pranskevichus1fa2ec42018-09-17 19:16:44 -0400290 it by one and return ``True`` immediately. If it is zero, wait
Yury Selivanov8be876e2018-09-11 17:10:37 -0700291 until a :meth:`release` is called and return ``True``.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100292
293 .. method:: locked()
294
295 Returns ``True`` if semaphore can not be acquired immediately.
296
Andrew Svetlovb79e0122015-05-08 14:13:41 +0300297 .. method:: release()
Victor Stinnerea3183f2013-12-03 01:08:00 +0100298
Yury Selivanov8be876e2018-09-11 17:10:37 -0700299 Release a semaphore, incrementing the internal counter by one.
300 Can wake up a task waiting to acquire the semaphore.
301
302 Unlike :class:`BoundedSemaphore`, :class:`Semaphore` allows
Elvis Pranskevichus1fa2ec42018-09-17 19:16:44 -0400303 making more ``release()`` calls than ``acquire()`` calls.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100304
305
Victor Stinner8c462c52014-01-24 18:11:43 +0100306BoundedSemaphore
Yury Selivanov8be876e2018-09-11 17:10:37 -0700307================
Victor Stinner8c462c52014-01-24 18:11:43 +0100308
Victor Stinnerea3183f2013-12-03 01:08:00 +0100309.. class:: BoundedSemaphore(value=1, \*, loop=None)
310
Yury Selivanov8be876e2018-09-11 17:10:37 -0700311 A bounded semaphore object. Not thread-safe.
Victor Stinnerea3183f2013-12-03 01:08:00 +0100312
Yury Selivanov8be876e2018-09-11 17:10:37 -0700313 Bounded Semaphore is a version of :class:`Semaphore` that raises
314 a :exc:`ValueError` in :meth:`~Semaphore.release` if it
315 increases the internal counter above the initial *value*.
Andrew Svetlov28d8d142017-12-09 20:00:05 +0200316
317
Yury Selivanov8be876e2018-09-11 17:10:37 -0700318---------
Andrew Svetlov28d8d142017-12-09 20:00:05 +0200319
Andrew Svetlov28d8d142017-12-09 20:00:05 +0200320
321.. deprecated:: 3.7
322
Yury Selivanov8be876e2018-09-11 17:10:37 -0700323 Acquiring a lock using ``await lock`` or ``yield from lock`` and/or
Andrew Svetlov28d8d142017-12-09 20:00:05 +0200324 :keyword:`with` statement (``with await lock``, ``with (yield from
Yury Selivanov8be876e2018-09-11 17:10:37 -0700325 lock)``) is deprecated. Use ``async with lock`` instead.