Node.js distributed locking based on Mongodb.
# Add to project
$ npm i mongo-distributed-locks
const DLocks = require('mongo-distributed-locks');
async function takeFee({ userId, fee }) {
let user = await User.findOne({ _id: userId });
user.balance -= fee;
return user.save();
}
function takeFeeWithLock(params) {
return DLocks.exec({
resource: 'createPayment',
id: params.userId,
fn: takeFee.bind(null, params)
});
}
function doWork() {
let userId = 'userId';
// current user balance is 60
return Promise.all([
takeFeeWithLock({ userId, fee: 10 }),
takeFeeWithLock({ userId, fee: 25 })
]);
// current user balance is 25
}
async function manageLockManually() {
let userId = 'userId';
let lock = await DLocks.lock({
resource: 'user',
id: userId
});
// current user balance is 60
try {
await takeFee({ userId, fee: 10 });
await takeFee({ userId, fee: 25 });
// current user balance is 25
}
finally {
await DLocks.unlock(lock);
}
}
-
static registerLoggerErrorFn(loggerErrorFn)
Registers logger error function (DLocks
can log a few error messages), if not providedconsole.error
is used`.loggerErrorFn
- logger error function. Example of usage:DLocks.registerLoggerErrorFn(logger.error.bind(logger));
-
static exec({ resource, id, fn })
Creates aDLocks
instance and executes itsexec
method. Shortcut forlet instance = new DLocks(params); instance.exec();
.resource
- operation: createPayment, or resource: user name.id
- id of the locking resource.fn
- function that does some operation on the locking resource.
-
static lock({ resource, id, fn })
Locks resource and returnslock
object. This method can be helpful when you need to manage lock manually. Accepts the same parameters as staticexec
. -
unlock(lock)
Unlocks the previously locked resource.lock
- previously generatedlock
object.
Alexander Mac
Licensed under the MIT license.