Safeguard
Developer Tools•

A license gate blocked a dependency: how do you replace it?

When a license policy denies a package already in use, a stepwise replacement beats a rewrite. Options, order of work, and what to record.

Safeguard Security Team
4 min read

Do not start by rewriting. First check whether you really need the package, whether a newer or older version has a different license, and whether an alternative exists. Wrap the old dependency behind a small interface, swap the implementation, and record the decision with a date.

Start with whether the block is right

Before you spend a sprint, confirm the finding. Check the declared license at the exact version in your lockfile, not at the latest version. Check whether the package is dual licensed, which can let you pick a permitted option. See dual licensed packages for how to record that. Check how the package reaches your product: build only, development only, or shipped. Our post on build time or shipped explains why that changes the answer.

If the block holds, pick one of five routes.

RouteWhen it fits
Different versionAn earlier or later release carries an acceptable license
ExceptionThe use is internal, or the risk is accepted with an expiry
Alternative packageA comparable library exists with an allowed license
Standard library or existing codeYou use a small part of the package
Write it yourselfThe need is narrow and the logic is simple

This is engineering guidance, not legal advice. Exceptions should go through your normal approval path.

Steps for a swap

  1. Find every use. Search the codebase for imports of the package, not just the manifest. Count the call sites and the distinct functions used. The count usually surprises people, in the good direction.
  2. Add a seam. Create a thin internal module that exposes only what you use. Point every call site at it. This step changes no behavior and can ship on its own.
  3. Pick the replacement. Check its license, its maintenance, and its own dependencies. A replacement that pulls in a denied transitive license solves nothing.
  4. Build the new implementation behind the seam. Keep the old one in place.
  5. Test behavior with the same inputs on both. Pay attention to edge cases such as encoding, time zones, errors and ordering.
  6. Switch the seam, remove the old package from the manifest, and regenerate the lockfile.
  7. Re-scan to confirm the denied license is gone from the inventory, including transitive entries.

Record what you did

A short entry in your decision log: package, version, license, why denied, route chosen, replacement, date, approver. A year later someone will ask why the team did not use the popular library, and the entry answers it. The fields in the license decision log post work well.

Prevent the next one

Most of these replacements happen because the license check ran late. If the package arrived through a pull request, the gate would have blocked it before it spread across 40 files. Run the license check on the pull request that adds the dependency, and block there. See turning on a license gate without breaking every build.

Try it yourself

Click through it at your own pace, or open it full screen. Watch where in the flow the block happens, since earlier is cheaper.

Safeguard's SBOM and dependency scanning builds a component inventory with license data, and policies and gates can block a pull request on a license rule you define. You can try a free scan at gold.safeguard.sh.

Quick check

How long should an exception last?

Give every exception an expiry date and an owner. Shorter is better, since the review cost is small compared with a forgotten risk.

Is a fork of the denied package a way out?

A fork keeps the original license, so it rarely solves a license problem. It adds a maintenance job on top.

Last reviewed: 19 October 2026.

Never miss an update

Weekly insights on software supply chain security, delivered to your inbox.

Self-healing security runs on Safeguard.

Your first fix PR is minutes away.

No sales call required, even your agent can complete the purchase over MCP.