Distributed locks for Django using Zookeeper
pip install django-zk-locks
django-zk-locks exposes one single the lock contextmanager and the locked decorator.
The locked decorator will wrap a django management command (subclasses of django.core.management.base.BaseCommand) or any function with the lock contextmanager:
from django.core.management.base import BaseCommand
from database_locks import locked
@locked
class Command(BaseCommand):
...
def handle(self, *args, **options):
self.stdout.write('Got the lock')
from database_locks import locked
class SomeClass:
def non_locked(self):
pass
@locked
def locked(self):
print('got lock')
from database_locks import lock
class SomeClass:
def non_locked(self):
pass
def locked(self):
with lock():
print('got lock')
Both lock and locked have the same optional args:
:param lock_name: unique name in DB for this function
There are also the following options you can specify in the project settings.py
- ZOOKEEPER_LOCKS_STATUS_FILE: file that will be updated with the lock status (default None). Useful when you have multiple shared-lock processes, to quickly inspect which one has the lock.
- ZOOKEEPER_LOCKS_ENABLED: set to False to globally disable locks (default True)
- ZOOKEEPER_LOCKS_HOSTS: connection string for Zookeeper, such as "localhost:2181,localhost:2182,localhost:2183"
Tox is used by the Github Action to test several python and django versions.
To quickly test locally, kick off a Zookeeper docker container:
- docker run -d --name locks-test
- -p 2181:2181 zookeeper:3.9
List available environments with tox -l and then run the one you want/have:
tox -e py310-dj42