CLI tool
sindresorhus/update-notifier avatar
sindresorhus/update-notifier

update-notifier for Node.js CLI Applications

Update notifications for your CLI app

1,810 stars161 forksJavaScriptBSD-2-Clause

At a glance

What is it?
update-notifier adds non-intrusive npm update messages to command-line applications without blocking startup. It uses cached results and a background child process, but its notification timing and npm-oriented assumptions require careful integration.
Who is it for?
Adopt update-notifier for an npm-distributed Node.js CLI when a deferred, configurable message is useful and an npm release is the relevant upgrade path. Do not adopt it for non-npm packages, mandatory upgrade enforcement, or environments where silent background network checks are unacceptable.
Can I use it commercially?
Yes. BSD-2-Clause is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 90 days ago.
What is it written in?
Mainly JavaScript, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on October 22, 2026, and from our analysis. They are not legal advice.

Editorial analysis

Why update-notifier fits npm-backed CLI tools

update-notifier solves a narrow problem for command-line packages: telling users when a newer npm version exists without interrupting the main command. It is intended for maintainers of Node.js CLI applications that are distributed through npm, including tools where users may install one version and keep using it for months. The README lists npm, Yeoman, AVA, XO, and Node GH among its users, although the count of downstream users is not a quality measure.

The package does not update the application itself. It reads the local package metadata, checks the configured npm dist-tag, caches the result, and makes a notification available to the CLI. That boundary is important. A notification can tell a user which version is newer, but the application still needs a separate installation or upgrade mechanism.

The module also treats updates as something to present quietly. Its default notification is deferred, its checks are rate-limited, and notifications occur only when the process is a TTY. This suits interactive terminals where a short message can appear after useful output. It does not fit a CLI that must enforce an upgrade, block execution until users update, or support package registries other than npm without replacing parts of the documented workflow.

The cached background-check architecture

The design separates the current process from the network operation. When the notifier starts, it checks whether the configured interval has elapsed. If a check is due, it starts an asynchronous npm lookup in an unref'ed child process. The result is persisted, and a later invocation reads that cached result into `notifier.update`. The README describes this as preventing an impact on package startup performance, although it does not provide independent timing measurements.

The package metadata must include `name` and `version`. The version used for comparison comes from the package object passed through `pkg`, while the latest version is selected from npm using `distTag`. The resulting object includes `latest`, `current`, `type`, and `name`. The documented update types are `latest`, `major`, `minor`, `patch`, `prerelease`, and `build`.

The first-run behavior is easy to misunderstand. Even if an update is available immediately, the notification waits until `updateCheckInterval` has passed. This delay is intentional according to the README, but it can make manual testing appear broken. The repository includes `example.js` as the suggested place to inspect the notification behavior. The child process is explicitly unref'ed, so an explicit `process.exit` does not cancel the check that is already running in its own process.

Installing update-notifier and making the first call

The repository lists Node.js `>=18` in `package.json` and uses ES modules. Install the package with the command shown in the README. The first real integration consists of importing the notifier, importing the application's package metadata, passing that metadata through `pkg`, and calling `notify()`.

bash
npm install update-notifier

The package is imported as an ES module. The README's basic example imports `package.json` with an import assertion, then creates a notifier and calls its convenience method:

js
import updateNotifier from 'update-notifier';
import packageJson from './package.json' assert {type: 'json'};

updateNotifier({pkg: packageJson}).notify();

On a first invocation, the check may be scheduled rather than displayed immediately because the notification interval has not elapsed. To inspect the update object directly, keep the notifier instance:

js
import updateNotifier from 'update-notifier';
import packageJson from './package.json' assert {type: 'json'};

const notifier = updateNotifier({pkg: packageJson});
console.log(notifier.update);

The value is `undefined` when no update is available. When an update is known, the documented shape includes `latest`, `current`, `type`, and `name`. The exact current result depends on the installed package metadata and npm's response, so the example should be read as API usage rather than a fixed output.

Controlling notification content and timing

The default interval is one day, expressed as `1000 * 60 * 60 * 24`. A maintainer can change it when constructing the notifier. The interval controls how often a check is considered due, not how quickly a newly detected update must be displayed. The README also documents `shouldNotifyInNpmScript`, which defaults to `false`, and `distTag`, which defaults to `'latest'`.

Applications can replace the default message with placeholders for the package name, current version, latest version, and update command:

js
const notifier = updateNotifier({
	pkg,
	updateCheckInterval: 1000 * 60 * 60 * 24 * 7
});

if (notifier.update) {
	notifier.notify({message: 'Run `{updateCommand}` to update.'});
}

This example changes the check interval to one week and prints the notifier's cached update state when present. The message placeholder is resolved by the library's notification path. A custom message also disables the special handling described for `isGlobal`, so a project that is commonly installed as a local dependency should consider whether the default global-install recommendation is appropriate.

`notify()` accepts `defer`, `message`, `isGlobal`, and `boxenOptions`. Deferred notification defaults to `true`, and box options are passed to `boxen`. The notification is restricted to TTY processes, which prevents the default message from being written in many pipes, redirected outputs, and non-interactive jobs.

User opt-outs and non-interactive environments

The package gives end users several ways to disable notifications. The documented config file is `~/.config/configstore/update-notifier-[your-module-name].json`, and setting its `optOut` property to `true` disables the notifier. The path is also exposed through `notifier.config.path`, which can be used when the application needs to explain or support that configuration.

Users can set `NO_UPDATE_NOTIFIER` to any value or pass `--no-update-notifier` for one run. Checks are skipped automatically in CI and when `NODE_ENV` is set to `test`. These behaviors reduce accidental noise in automation, but they also mean a developer may see no message even when the integration is configured correctly.

The opt-out file is specific to the module name, while the environment variable and command-line flag apply without editing that file. The README does not document how conflicts are resolved, how the notification behaves in unusual terminal emulators, or what happens when the configstore file is unreadable or malformed. Those cases require inspection during integration rather than assuming a documented recovery path.

Limits, licensing, and maintenance considerations

The main limitation is the mismatch between “notifier” and “updater.” update-notifier can report that `latest` differs from the current version, but it cannot make the installation change. Teams that need automatic replacement, mandatory minimum versions, or rollback behavior need additional tooling. The README does not document rollback.

There is also a timing limitation during development. The first check does not produce an immediate notification, so a short test run may only show the caching behavior. The README points to `example.js` for a faster way to see the feature. Applications must decide whether a weekly interval is acceptable, whether `latest` is the right dist-tag, and whether a deferred message should be shown in their own output.

The repository is not archived, and the last push was on 2026-07-25. Recent releases include v7.3.1 on 2024-09-09, v7.2.0 on 2024-07-26, and v7.3.1 as the package version in `package.json`. The package is licensed under BSD-2-Clause. That license permits use and modification under its stated terms, but the notification output, npm installation behavior, and your package's distribution terms still need to be reviewed for the actual project.

Node.js `>=18` is required by `package.json`. The declared dependencies include `boxen`, `chalk`, `configstore`, `latest-version`, `semver`, and related modules, so upgrading the application also means accounting for its dependency tree and any changes in Node.js compatibility.

Editorial conclusion

Adopt update-notifier for an npm-distributed Node.js CLI when a deferred, configurable message is useful and an npm release is the relevant upgrade path. Do not adopt it for non-npm packages, mandatory upgrade enforcement, or environments where silent background network checks are unacceptable. Check TTY behavior, the `distTag`, notification timing, user opt-out settings, and your chosen update command before shipping the integration.

Frequently asked questions

How do I install update-notifier in a Node.js CLI project?

The README instructs users to run `npm install update-notifier`. The package requires Node.js `>=18` and is an ES module, as shown in `package.json`.

Why does my update notification not appear on the first run?

The README says the first check waits until `updateCheckInterval` has elapsed before notifying, even if an update is already available. The default interval is one day.

Can users disable update-notifier?

Yes. Users can set `optOut` to `true` in the module-specific configstore file, set `NO_UPDATE_NOTIFIER`, or pass `--no-update-notifier`. Checks are also skipped in CI and when `NODE_ENV` is `test`.

Official sources

  1. Issues
  2. License: BSD-2-Clause
  3. README
  4. Releases
  5. sindresorhus/update-notifier on GitHub
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/sindresorhus-update-notifier.svg)](https://hysenlabs.com/projects/sindresorhus-update-notifier)

Was this useful?