Skip to content

createMutex

Creates a mutex: a lock allowing at most one holder at a time, queueing excess acquire() callers in FIFO order. A createSemaphore with a single permit.

A factory function rather than a class, matching this package’s other stateful helpers (debounce, throttle): the returned object closes over an internal semaphore.

Typical use: deduplicating concurrent callers of a non-reentrant operation, e.g. making sure only one in-flight token-refresh call happens at a time while others wait for it.

Available since v3.0.4

import { createMutex } from '@helpers4/promise';
// or, from the all-in-one package (same code, one install):
import { createMutex } from 'helpers4/promise';
createMutex(): Mutex

Mutex — A Mutex

Only one caller actually refreshes; the rest wait and reuse its result.

const mutex = createMutex();
let cached: string | undefined;

async function getToken() {
  return mutex.run(async () => {
    if (cached) return cached;
    cached = await refreshToken(); // only ever runs once per cache miss
    return cached;
  });
}

await Promise.all([getToken(), getToken(), getToken()]);
// refreshToken() was called exactly once

isLocked() reports whether the lock is currently held

Section titled “isLocked() reports whether the lock is currently held”

Useful for diagnostics or conditionally skipping work while locked.

const mutex = createMutex();
mutex.isLocked() // => false
const release = await mutex.acquire();
mutex.isLocked() // => true
release();
mutex.isLocked() // => false

A mutex created by createMutex.

interface Mutex {
  acquire(): Promise<Release>;
  isLocked(): boolean;
  run<T>(fn: function): Promise<T>;
}

View source on GitHub