Skip to content

Commit 8d8c8e7

Browse files
committed
updated license and readme
1 parent f074079 commit 8d8c8e7

File tree

2 files changed

+84
-14
lines changed

2 files changed

+84
-14
lines changed

LICENSE

Lines changed: 11 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -2,20 +2,19 @@ The MIT License (MIT)
22

33
Copyright (c) 2014 Ambition
44

5-
Permission is hereby granted, free of charge, to any person obtaining a copy
6-
of this software and associated documentation files (the "Software"), to deal
7-
in the Software without restriction, including without limitation the rights
8-
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9-
copies of the Software, and to permit persons to whom the Software is
10-
furnished to do so, subject to the following conditions:
5+
Permission is hereby granted, free of charge, to any person obtaining a copy of
6+
this software and associated documentation files (the "Software"), to deal in
7+
the Software without restriction, including without limitation the rights to
8+
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
9+
the Software, and to permit persons to whom the Software is furnished to do so,
10+
subject to the following conditions:
1111

1212
The above copyright notice and this permission notice shall be included in all
1313
copies or substantial portions of the Software.
1414

1515
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16-
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17-
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18-
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19-
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20-
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21-
SOFTWARE.
16+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
17+
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
18+
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
19+
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
20+
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

README.md

Lines changed: 73 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,75 @@
1+
[![Build Status](https://travis-ci.org/ambitioninc/django-db-mutex.png)](https://travis-ci.org/ambitioninc/django-db-mutex)
12
django-db-mutex
2-
===============
3+
=====================
34

4-
Acquire a mutex via the DB in Django
5+
Provides the ability to acquire a mutex lock from the database in Django.
6+
7+
## A Brief Overview
8+
For critical pieces of code that cannot overlap with one another, it is often necessary to acquire a mutex lock of some sort. Many solutions use a memcache lock strategy, however, this strategy can be brittle in the case of memcache going down or when an unconsistent hashing function is used in a distributed memcache setup.
9+
10+
If your application does not need a high performance mutex lock, Django DB Mutex does the trick. The common use case for Django DB Mutex is to provide the abilty to lock long-running periodic tasks that should not overlap with one another. Celery is the common backend for Django when scheduling periodic tasks.
11+
12+
## How to Use Djagno DB Mutex
13+
The Djagno DB Mutex app provides a context manager and function decorator for locking a critical section of code. The context manager is used in the following way:
14+
15+
from db_mutex import db_mutex, DBMutexError, DBMutexTimeoutError
16+
17+
# Lock a critical section of code
18+
try:
19+
with db_mutex('lock_id'):
20+
# Run critical code here
21+
pass
22+
except DBMutexError:
23+
print 'Could not obtain lock'
24+
except DBMutexTimeoutError:
25+
print 'Task completed but the lock timed out'
26+
27+
You'll notice that two errors were caught from this context manager. The first one, DBMutexError, is thrown if the lock cannot be acquired. The second one, DBMutexTimeoutError, is thrown if the critical code completes but the lock timed out. More about lock timeout in the next section.
28+
29+
The db_mutex decorator can also be used in a similar manner for locking a function.
30+
31+
from db_mutex import db_mutex, DBMutexError, DBMutexTimeoutError
32+
33+
@db_mutex('lock_id')
34+
def critical_function():
35+
pass
36+
37+
try:
38+
critical_function()
39+
except DBMutexError:
40+
print 'Could not obtain lock'
41+
except DBMutexTimeoutError:
42+
print 'Task completed but the lock timed out'
43+
44+
## Lock Timeout
45+
Django DB Mutex comes with lock timeout baked in. This ensures that a lock cannot be held forever. This is especially important when working with segments of code that may run out of memory or produce errors that do not raise exceptions.
46+
47+
In the default setup of this app, a lock is only valid for 30 minutes. As shown earlier in the example code, if the lock times out during the execution of a critical piece of code, a DBMutexTimeoutError will be thrown. This error basically says that a critical section of your code could have overlapped (but it doesn't necessarily say if a section of code overlapped or didn't).
48+
49+
In order to change the duration of a lock, set the DB_MUTEX_TTL_SECONDS variable in your settings.py file to a number of seconds. If you want your locks to never expire (beware!), set the setting to None.
50+
51+
## Usage with Celery
52+
Django DB Mutex can be used with celery's tasks in the following manner.
53+
54+
from celery import Task
55+
56+
class NonOverlappingTask(Task):
57+
def run_worker(self, *args, **kwargs):
58+
"""
59+
Run worker code here.
60+
"""
61+
raise NotImplementedError()
62+
63+
def run(self, *args, **kwargs):
64+
try:
65+
with db_mutex(self.__class__.__name__):
66+
self.run_worker(*args, **kwargs):
67+
except DBMutexError:
68+
# Ignore this task since the same one is already running
69+
pass
70+
except DBMutextTimeoutError:
71+
# A task ran for a long time and another one may have overlapped with it. Report the error
72+
pass
73+
74+
## License
75+
MIT License (see the LICENSE file included in the repository)

0 commit comments

Comments
 (0)