fifolock

A flexible low-level tool to make synchronisation primitives in asyncio Python. As the name suggests, locks are granted strictly in the order requested: first-in-first-out; and are not reentrant.
Installation
pip install fifolock
Recipes
Mutex (exclusive) lock
import asyncio
from fifolock import FifoLock
class Mutex(asyncio.Future):
@staticmethod
def is_compatible(holds):
return not holds[Mutex]
lock = FifoLock()
async def access():
async with lock(Mutex):
# access resource
Read/write (shared/exclusive) lock
import asyncio
from fifolock import FifoLock
class Read(asyncio.Future):
@staticmethod
def is_compatible(holds):
return not holds[Write]
class Write(asyncio.Future):
@staticmethod
def is_compatible(holds):
return not holds[Read] and not holds[Write]
lock = FifoLock()
async def read():
async with lock(Read):
# shared access
async def write():
async with lock(Write):
# exclusive access
Semaphore
import asyncio
from fifolock import FifoLock
class SemaphoreBase(asyncio.Future):
@classmethod
def is_compatible(cls, holds):
return holds[cls] < cls.size
lock = FifoLock()
Semaphore = type('Semaphore', (SemaphoreBase, ), {'size': 3})
async def access():
async with lock(Semaphore):
# at most 3 concurrent accesses
Running tests
python setup.py test
Design choices
Each mode of the lock is a subclass of asyncio.Future. This could be seen as a leak some of the internals of FifoLock, but it allows for clear client and internal code.
-
Classes are hashable, so each can be a key in the
holdsdictionary passed to theis_compatiblemethod. This allows the compatibility conditions to be read clearly in the client code, and theholdsdictionary to be mutated clearly internally. -
An instance of it, created inside
FifoLock, is both the object awaited upon, and stored in a deque with a way of accessing itsis_compatiblemethod. -
The fact it's a class and not an instance of a class also makes clear it is to store no state, merely configuration.
A downside is that for configurable modes, such as for a semaphore, the client must dynamically create a class: this is not a frequently-used pattern.
The fact that the lock is not reentrant is deliberate: the class of algorithms this is designed for does not require this. This would add unnecessary complexity, and presumably be slower.
Metadata
Release files for fifolock 0.0.20
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| fifolock-0.0.20.tar.gz | 2.9 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| fifolock-0.0.20-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 6.6 kB
Release files / fifolock-0.0.20.tar.gz
| Download URL | fifolock-0.0.20.tar.gz |
|---|---|
| Size | 2.9 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
c38ac427605d87936a6131524aa2a1ef2964f12892e76c1749b136b9e53a88f9
|
|
BLAKE2b-256 checksum How to use checksums |
a5d1e7272af6b1b956460ce2ecde67522cf8715832d1c3f63f97d3bba318329f
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/1.12.1 pkginfo/1.4.2 requests/2.21.0 setuptools/40.4.3 requests-toolbelt/0.8.0 tqdm/4.28.1 CPython/3.7.1
|
Release files / fifolock-0.0.20-py3-none-any.whl
| Download URL | fifolock-0.0.20-py3-none-any.whl |
|---|---|
| Size | 3.8 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
48ce70e50ceecd799e0346b6a92bb1d0301fd6b9ebeb3a2b3383e0ca7c3e73f5
|
|
BLAKE2b-256 checksum How to use checksums |
574b9496f5c90796fb56217cf9f6fde868eb19d6788fb5c2ea5d5fa97db36579
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/1.12.1 pkginfo/1.4.2 requests/2.21.0 setuptools/40.4.3 requests-toolbelt/0.8.0 tqdm/4.28.1 CPython/3.7.1
|