The Safest Dependency Update May Be the One You Delay

The Safest Dependency Update May Be the One You Delay

~ 6 min read


For years, dependency hygiene has been reduced to a simple rule: newer is safer. An automated pull request appears, the test suite passes and the update is merged before it can become technical debt.

That rule ignores the riskiest moment in a package release’s life: the first few hours, when almost nobody has inspected or used it.

GitHub has now made a three-day cooldown the default for Dependabot version updates. Security updates still open immediately. Routine releases must first spend three days in the registry.

This is a good default because release age is useful security information. Delaying a routine update is not the same as neglecting it. A short, deliberate delay lets the wider ecosystem test an artefact before it enters your build.

Freshness Is Not Evidence

Automated dependency tools usually know that a release is newer. They can inspect its declared version, dependency graph, advisory status and perhaps its provenance. They cannot know that the maintainer’s account was compromised ten minutes before publication or that an obfuscated payload has not yet been reported.

Time helps with the unknown part.

In September 2025, an attacker phished an npm maintainer and published malicious versions of packages including chalk and debug. According to GitHub’s account of the incident, the poisoned versions were available for roughly two hours before the community identified them and npm removed them.

Two hours was an effective response from the ecosystem. It was also plenty of time for an update bot to find the release, open a pull request and hand a green build to a team accustomed to merging green builds.

A three-day delay would not have detected the malware. It would simply have prevented most Dependabot users from being among its earliest consumers. Maintainers, registry operators, security researchers and less cautious adopters supplied the missing evidence while everyone else waited.

A newly released package moving through a sequence of observation gates before reaching a protected application

That is the useful property of a cooldown: it converts public scrutiny into a passive control. The cost is a small amount of version lag. The potential benefit is avoiding a compromised or badly broken release that disappears before the delay ends.

Security Updates Need a Different Clock

The strongest objection to delayed updates is obvious. Old dependencies contain vulnerabilities, so waiting sounds like choosing exposure.

That argument combines two different queues.

A Dependabot security update responds to a known vulnerability. The current version has an identified problem and a patched version exists. GitHub’s default cooldown does not apply to these updates, because delaying a known fix would preserve a known risk.

A version update has a different purpose. It keeps a dependency current even when the installed version has no published vulnerability. The decision is between a version you already operate and a newer release with less field evidence.

The safest policy is therefore asymmetric:

  • Move quickly when an advisory makes the existing version unsafe.
  • Add a short observation window when a routine release is merely newer.

Urgency should come from evidence, not from the existence of a higher version number.

Three Days Is a Starting Point

GitHub chose three days because many fast-moving package compromises are detected and withdrawn within hours. It is a sensible platform default, but it should not become another unexplained constant copied into every repository.

The appropriate delay depends on what is being updated.

A patch for a widely used development tool might need only the default window. A major release of a runtime dependency deserves longer because the compatibility risk is higher even when the package is benign. A private package published by the same organisation may use a shorter path if its accounts, build system and registry are already inside the team’s trust boundary.

Dependabot’s cooldown configuration supports different windows for major, minor and patch updates, plus package include and exclude rules:

version: 2
updates:
    - package-ecosystem: "npm"
      directory: "/"
      schedule:
          interval: "daily"
      cooldown:
          default-days: 7
          semver-major-days: 30
          semver-minor-days: 7
          semver-patch-days: 3
          exclude:
              - "@your-company/*"

This policy still checks for releases daily. It delays when Dependabot considers them eligible for a version-update pull request. Security updates remain outside the cooldown.

The private namespace exclusion is not automatically correct. Internal registries can be compromised too. It only makes sense when the organisation can justify why those packages have a different release and trust process.

Delay Is Not a Complete Defence

A cooldown is effective against malicious or broken versions that are discovered quickly. It does little against a patient backdoor, maintainer sabotage that looks legitimate, or a compromised build pipeline that keeps producing apparently valid releases.

It also does not inspect the update on your behalf. After the delay, a pull request can still introduce a vulnerable transitive dependency, an unwanted install script or a breaking change that the existing tests miss.

Several defensive layers surrounding a dependency after its waiting period, with no single layer carrying the whole load

Keep the controls that were necessary before cooldowns existed:

  • Commit and enforce lockfiles so CI installs the reviewed dependency graph.
  • Disable package install scripts where the application can work without them.
  • Give build and release tokens the smallest useful scope.
  • Review surprising dependency, script and lockfile changes.
  • Run tests that exercise integration boundaries rather than merely proving the application compiles.

The delay buys better evidence. It does not turn the eventual update into trusted code.

A Healthy Team Can Wait Without Falling Behind

The other failure mode is using safety language to excuse indefinite lag. A seven-day cooldown is a policy. A seven-month backlog is deferred maintenance.

Keep update checks frequent even when eligibility is delayed. Group low-risk changes into a predictable review window. Track old pull requests and failed upgrades. Give major updates an owner before they become emergency migrations.

Teams that need early compatibility feedback can also split observation from adoption. A canary repository or non-production integration environment can test new releases immediately while the production dependency policy retains its cooldown. The team still learns early without making every production build an involuntary early adopter.

The useful metric is not how quickly a bot opened the pull request. It is how reliably the team moves to a well-observed release before the installed version becomes a liability.

Let Someone Else Be First

Software engineering often rewards speed, but dependency adoption is not a race with a prize for first place. The first consumers of a release receive the least evidence and the largest share of its unknown risk.

GitHub’s new default recognises that automation should not remove every pause from a delivery system. Some pauses are friction. Others are where information arrives.

Keep known security fixes fast. Give routine versions a small, explicit cooldown. Then review them with the same care as any other external code entering the application.

all posts →