In 2023, npm continued refining its package unpublish policies—a long-running effort to balance maintainer autonomy with ecosystem stability. The changes may seem administrative, but they touch on one of the most underappreciated risks in software supply chains: what happens when a dependency disappears.
The Left-Pad Legacy
If you've been in the JavaScript ecosystem for a while, you remember left-pad. In March 2016, developer Azer Koçulu unpublished over 250 packages from npm after a dispute with the npm team over a package name. One of those packages, left-pad—an 11-line function that pads strings—was depended upon by thousands of packages, including React, Babel, and countless others.
The unpublish broke builds worldwide. npm intervened by un-unpublishing the package, setting a precedent that the registry would act to protect ecosystem stability.
Since then, npm has progressively tightened its unpublish rules. The current policy allows unpublishing only within 72 hours of publishing, and only if the package version has no dependents. Beyond 72 hours, packages cannot be unpublished—only deprecated.
2023 Policy Refinements
The 2023 updates further clarified and tightened these rules:
Stronger dependency checks. npm now performs more thorough dependency analysis before allowing unpublish. If any public package depends on the version you're trying to unpublish—even transitively—the operation is blocked.
Improved deprecation workflows. Since unpublish is restricted, npm improved the deprecation flow. Deprecated packages now display more prominent warnings during npm install, and the registry surfaces deprecation notices in the web UI more clearly.
Transfer over delete. npm now more actively encourages package transfers rather than deletion. If a maintainer wants to abandon a package, npm provides mechanisms to transfer ownership to another maintainer or to the npm team itself.
The Security Angle
The unpublish restrictions aren't just about build stability—they're a supply chain security measure. Consider these attack scenarios:
Package squatting after unpublish. If a popular package is unpublished, an attacker can register the same name and publish a malicious version. Every project that runs npm install without a lockfile would pull the attacker's package. This has happened in practice.
Dependency confusion via unpublish. In organizations using private npm registries alongside the public registry, unpublishing a public package creates an opportunity for dependency confusion. If the organization has an internal package with the same name, the resolution behavior can be exploited.
Protest-ware through deprecation. While unpublish is restricted, maintainers can still publish new versions with arbitrary code. The node-ipc incident in March 2022—where the maintainer added code that corrupted files on systems with Russian or Belarusian IP addresses—showed that malicious updates from legitimate maintainers are a real threat.
What This Means for Your Security Posture
Lock your dependencies. Using package-lock.json (or yarn.lock / pnpm-lock.yaml) ensures that builds are reproducible and that unpublished or replaced packages don't silently change what you're running. This should be non-negotiable.
Verify package integrity. npm's --before flag lets you install packages as they existed at a specific point in time. Combined with Subresource Integrity (SRI) hashes in lockfiles, this provides strong guarantees about package contents.
Monitor for ownership changes. A change in package ownership can signal a supply chain attack. If a widely-used package suddenly gets a new maintainer who pushes updates, that warrants investigation.
Use a private registry mirror. Tools like Verdaccio, Artifactory, or npm Enterprise allow you to mirror packages locally. This protects your builds from upstream outages and gives you control over what packages are available in your organization.
Audit your transitive dependencies. The left-pad incident illustrated how a tiny, deeply-nested dependency can have outsized impact. You need visibility into your full dependency tree, not just your direct dependencies.
The Broader Ecosystem Trend
npm's policy changes reflect a broader recognition across package registries that ecosystem stability is a shared responsibility. PyPI has implemented similar restrictions on package deletion. Maven Central has always been immutable—once published, artifacts cannot be removed or modified. Cargo (Rust) allows "yanking" versions but keeps the tarball available for existing dependents.
The trend is clear: package registries are moving toward immutability. This is good for supply chain security, but it also means that the initial publish of a package carries more weight. Malicious packages that slip past initial review will persist longer, making proactive scanning more important than ever.
The Maintainer Perspective
It's worth acknowledging the tension here. Maintainers have legitimate reasons to want to remove packages—accidentally published secrets, legal disputes, burnout, or simply not wanting to maintain something anymore. The restrictions on unpublish can feel like a loss of control over their own work.
The open-source community needs to find better answers for maintainer sustainability. Security ultimately depends on the health and well-being of the people writing and maintaining the code we all depend on.
How Safeguard.sh Helps
Safeguard.sh continuously monitors your npm dependencies for changes that could indicate supply chain risk—including ownership transfers, sudden bursts of new versions, deprecation notices, and anomalous publish patterns. Our SBOM tracking gives you complete visibility into your transitive dependency tree, and our alerting ensures you're notified when any dependency in your graph changes in a way that warrants investigation. By maintaining a historical record of your dependency state, Safeguard.sh helps you detect and respond to supply chain events before they become incidents.