Socket
Socket
Sign inDemoInstall

proper-lockfile

Package Overview
Dependencies
4
Maintainers
1
Versions
33
Alerts
File Explorer

Advanced tools

Install Socket

Detect and block malicious and high-risk dependencies

Install

proper-lockfile


Version published
Maintainers
1
Created

Package description

What is proper-lockfile?

The proper-lockfile npm package is used to create and manage file locks, ensuring that only one process can access a file at a time. This is particularly useful for preventing race conditions and ensuring data integrity in concurrent environments.

What are proper-lockfile's main functionalities?

Locking a file

This feature allows you to lock a file to prevent other processes from accessing it. The code sample demonstrates how to lock a file, perform some operations, and then release the lock.

const lockfile = require('proper-lockfile');

async function lockFile() {
  try {
    const release = await lockfile.lock('somefile');
    console.log('File is locked');
    // Do some work with the locked file
    await release();
    console.log('File is released');
  } catch (err) {
    console.error('Failed to lock file', err);
  }
}

lockFile();

Checking if a file is locked

This feature allows you to check if a file is currently locked. The code sample demonstrates how to check the lock status of a file.

const lockfile = require('proper-lockfile');

async function checkLock() {
  try {
    const isLocked = await lockfile.check('somefile');
    console.log(`File is ${isLocked ? 'locked' : 'not locked'}`);
  } catch (err) {
    console.error('Failed to check lock status', err);
  }
}

checkLock();

Unlocking a file

This feature allows you to manually unlock a file. The code sample demonstrates how to unlock a file that was previously locked.

const lockfile = require('proper-lockfile');

async function unlockFile() {
  try {
    await lockfile.unlock('somefile');
    console.log('File is unlocked');
  } catch (err) {
    console.error('Failed to unlock file', err);
  }
}

unlockFile();

Other packages similar to proper-lockfile

Readme

Source

proper-lockfile

NPM version Downloads Build Status Coverage Status Dependency status Dev Dependency status

A inter-process and inter-machine lockfile utility that works on a local or network file system.

Installation

$ npm install proper-lockfile --save

Design

There are various ways to achieve file locking.

This library utilizes the mkdir strategy which works atomically on any kind of file system, even network based ones. The lockfile path is based on the file path you are trying to lock by suffixing it with .lock.

When a lock is successfully acquired, the lockfile's mtime (modified time) is periodically updated to prevent staleness. This allows to effectively check if a lock is stale by checking its mtime against a stale threshold. If the update of the mtime fails several times, the lock might be compromised. The mtime is supported in almost every filesystem.

Comparison

This library is similar to lockfile but the later has some drawbacks:

  • It relies on open with O_EXCL flag which has problems in network file systems. proper-lockfile uses mkdir which doesn't have this issue.

O_EXCL is broken on NFS file systems; programs which rely on it for performing locking tasks will contain a race condition.

  • The lockfile staleness check is done via ctime (creation time) which is unsuitable for long running processes. proper-lockfile constantly updates lockfiles mtime to do proper staleness check.

  • It does not check if the lockfile was compromised which can led to undesirable situations. proper-lockfile checks the lockfile when updating the mtime.

Compromised

proper-lockfile does not detect cases in which:

  • A lockfile is manually removed and someone else acquires the lock right after
  • Different stale/update values are being used for the same file, possibly causing two locks to be acquired on the same file

proper-lockfile detects cases in which:

  • Updates to the lockfile fail
  • Updates take longer than expected, possibly causing the lock to became stale for a certain amount of time

As you see, the first two are a consequence of bad usage. Technically, it was possible to detect the first two but it would introduce complexity and eventual race conditions.

Usage

.lock(file, [options], [compromised], callback)

Tries to acquire a lock on file.

If the lock succeeds, a release function is provided that should be called when you want to release the lock.
If the lock gets compromised, the compromised function will be called. The default compromised function is a simple throw err which will probably cause the process to die. Specify it to handle the way you desire.

Available options:

  • stale: Duration in milliseconds in which the lock is considered stale, defaults to 10000 (minimum value is 5000)
  • update: The interval in milliseconds in which the lockfile's mtime will be updated, defaults to stale/2 (minimum value is 1000, maximum value is stale/2)
  • retries: The number of retries or a retry options object, defaults to 0
  • realpath: Resolve symlinks using realpath, defaults to true (note that if true, the file must exist previously)
  • fs: A custom fs to use, defaults to graceful-fs
var lockfile = require('proper-lockfile');

lockfile.lock('some/file', function (err, release) {
    if (err) throw err;      // Lock failed

    // Do something while the file is locked

    // Call the provided release function when you're done
    release();

    // Note that you can optionally handle release errors
    // Though it's not mandatory since it will eventually stale
    /*release(function (err) {
        // At this point the lock was effectively released or an error
        // ocurred while removing it
        if (err) throw err;
    });*/
});

.unlock(file, [options], [callback])

Releases a previously acquired lock on file.

Whenever possible you should use the release function instead (as exemplified above). Still there are cases in which its hard to keep a reference to it around code. In those cases unlock() might be handy.

The callback is optional because even if the removal of the lock failed, the lockfile's mtime will no longer be updated causing it to eventually stale.

Available options:

  • realpath: Resolve symlinks using realpath, defaults to true (note that if true, the file must exist previously)
  • fs: A custom fs to use, defaults to graceful-fs
var lockfile = require('proper-lockfile');

lockfile.lock('some/file', function (err) {
    if (err) throw err;

    // Later..
    lockfile.unlock('some/file');

    // or..
    /*lockfile.unlock('some/file', function (err) {
        // At this point the lock was effectively released or an error
        // ocurred while removing it
        if (err) throw err;
    });*/
});

.lockSync(file, [options], [compromised])

Sync version of .lock().
Returns the release function or throws on error.

.unlockSync(file, [options])

Sync version of .unlock().
Throws on error.

Graceful exit

proper-lockfile automatically remove locks if the process exists. Though, SIGINT and SIGTERM signals are handled differently by nodejs in the sense that they do not fire a exit event on the process. To avoid this common issue that CLI developers have, please do the following:

// Map SIGINT & SIGTERM to process exit
// so that lockfile removes the lockfile automatically
process
.once('SIGINT', function () {
    process.exit(1);
})
.once('SIGTERM', function () {
    process.exit(1);
});

Tests

$ npm test
$ npm test-cov to get coverage report

The test suite is very extensive. There's even a stress test to guarantee exclusiveness of locks.

License

Released under the MIT License.

Keywords

FAQs

Last updated on 26 Jan 2016

Did you know?

Socket

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Install

Related posts

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap

Packages

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc