Files
plm-lottery/app/tx/locks.py
T

23 lines
798 B
Python
Raw Normal View History

import asyncio
from contextlib import asynccontextmanager
class UserLocks:
"""Per-user asyncio.Lock registry, shared by PLAY and WITHDRAW so a user can
never have a bet-build and a withdrawal-build in flight at once (both would
otherwise spend from the same UTXO set on the user's dedicated address).
Single-process-only by design (an in-memory dict of asyncio.Lock) — this is an
accepted MVP constraint; a multi-process deployment would need a DB or Redis
lock instead (e.g. a Postgres advisory lock).
"""
def __init__(self) -> None:
self._locks: dict[int, asyncio.Lock] = {}
@asynccontextmanager
async def acquire(self, user_id: int):
lock = self._locks.setdefault(user_id, asyncio.Lock())
async with lock:
yield