Command-line tools
npm UNABLE_TO_GET_ISSUER_CERT_LOCALLY: fix npm install
npm ERR! code UNABLE_TO_GET_ISSUER_CERT_LOCALLYUNABLE_TO_GET_ISSUER_CERT_LOCALLY means the HTTPS certificate presented for the npm registry chains to a root that Node.js does not trust. On most machines that is a corporate proxy re-signing traffic, or a private registry using an internal CA.
Quick fix
Adding the company root with NODE_EXTRA_CA_CERTS fixes most cases.
Find out who signed the certificate npm sees, here or with the certificate decoder:
npm config get registry
openssl s_client -connect registry.npmjs.org:443 -servername registry.npmjs.org </dev/null 2>/dev/null | openssl x509 -noout -issuer
If the issuer is your company or a security vendor, get that root (PEM) from IT and add it for every Node.js process:
export NODE_EXTRA_CA_CERTS=/path/to/company-root.pem
npm install
Make it permanent in your shell profile, CI variables or Dockerfile. Alternatively, configure npm only:
npm config set cafile /path/to/ca-bundle.pem # must include all roots npm needs
Newer npm versions print npm error code UNABLE_TO_GET_ISSUER_CERT_LOCALLY; the fix is the same.
Causes
1. Corporate proxy or antivirus HTTPS inspection
- Confirm: the issuer printed above is not a public CA; the error appears only on the company network or VPN.
- Fix: add the proxy root with
NODE_EXTRA_CA_CERTS. If npm also needs a proxy address, setnpm config set proxyandhttps-proxyto the URL IT gives you.
2. Private registry with an internal CA
Nexus, Artifactory, Verdaccio or GitLab package registries often use certificates from an internal CA.
- Confirm:
npm config get registryshows an internal host; the issuer is your internal CA. - Fix: trust the internal root via
NODE_EXTRA_CA_CERTS, or scopecafilein the project.npmrc. If the registry sends an incomplete chain, the error is unable to verify the first certificate instead; fix the registry's reverse proxy.
3. A ca or cafile setting that replaced the defaults
- Confirm:
npm config listshowscaorcafile, possibly from a project, user or global.npmrc. - Fix: make that file contain all roots needed (public and private), or remove it and use
NODE_EXTRA_CA_CERTS.
4. Old Node.js or npm
Old releases ship outdated CA lists.
- Fix: upgrade to a supported Node.js LTS release, which bundles a current Mozilla CA list.
5. A stale or retired mirror
Project or user .npmrc files tend to outlive the mirrors they point to. A mirror that moved to a new domain, or an internal mirror whose certificate was replaced by an internally signed one, produces this error or a related one such as CERT_HAS_EXPIRED.
- Confirm:
npm config get registryandnpm config listshow a host you did not expect;npm pingfails for it. - Fix: point the registry at the current URL with
npm config set registry <url>, or delete the stale line from the.npmrcthat sets it.
Fixes by environment
Every environment uses the same fix: point NODE_EXTRA_CA_CERTS or npm's cafile at a PEM file with the missing root. Node.js code outside npm fails the same way, see UNABLE_TO_GET_ISSUER_CERT_LOCALLY in Node.js.
Windows: setx NODE_EXTRA_CA_CERTS C:\certs\company-root.pem, then open a new terminal. Export the root from the Windows store in Base-64 (PEM) format first.
macOS / Linux: add export NODE_EXTRA_CA_CERTS=... to ~/.zshrc or ~/.bashrc.
Docker:
COPY company-root.pem /usr/local/share/ca-certificates/company-root.crt
ENV NODE_EXTRA_CA_CERTS=/usr/local/share/ca-certificates/company-root.crt
RUN npm ci
CI (GitHub Actions, GitLab CI, Jenkins): store the PEM as a file secret and export NODE_EXTRA_CA_CERTS before npm ci.
Packages with postinstall downloads (for example browser or native binaries fetched during install) use their own HTTPS requests, so only NODE_EXTRA_CA_CERTS covers them, not npm's cafile.
Don't do this
npm config set strict-ssl false. npm will accept any certificate for the registry, so a man-in-the-middle can serve modified packages that run code on your machine through install scripts.NODE_TLS_REJECT_UNAUTHORIZED=0 npm install. Same risk, for every connection made during install.- Switching the registry to
http://. Removes encryption and integrity in transit entirely.
FAQ
Should I use cafile or NODE_EXTRA_CA_CERTS?
cafile is read by npm itself and, like the ca setting, replaces npm's default CA list for registry requests, so the file must contain every root you need. NODE_EXTRA_CA_CERTS adds certificates to Node's defaults for every Node.js process, which also fixes postinstall scripts that download binaries. Behind a corporate proxy, NODE_EXTRA_CA_CERTS is usually the less surprising choice.
Why does the error appear only on the office network?
Your company proxy is decrypting HTTPS and re-signing it with its own root. At home you connect to the registry directly and see its public certificate. Ask IT for the proxy's root certificate.
Do yarn and pnpm need separate settings?
They run on Node.js, so NODE_EXTRA_CA_CERTS works for all of them. Each also has its own CA setting (for example yarn's cafile and Yarn Berry's caFilePath), which you only need if you prefer per-tool configuration.
How do I check which registry npm is using?
Run npm config get registry. A typo in a mirror URL or a stale project-level .npmrc pointing at an old internal registry is a common hidden cause.