This error occurs when Node.js attempts to make an HTTPS request but cannot verify the SSL/TLS certificate because it is self-signed or issued by an untrusted Certificate Authority. This is common in corporate networks, development environments, or when connecting to private registries.
This error indicates that Node.js's built-in TLS/SSL verification has rejected a certificate during an HTTPS connection attempt. Node.js maintains a list of trusted Certificate Authorities (CAs) and validates all certificates against this list by default. When you encounter this error, it means the certificate presented by the server is either self-signed (not issued by a recognized CA) or part of a certificate chain that cannot be traced back to a trusted root CA. This is Node.js protecting you from potentially insecure connections. While certificate errors often indicate legitimate security concerns, they can also occur in controlled environments where self-signed certificates are intentionally used, such as internal corporate networks, development/staging servers, or private package registries.
Before bypassing certificate validation, confirm this is expected behavior and not a security issue:
# Check certificate details
openssl s_client -connect example.com:443 -showcerts
# Look for "Verify return code" in the output
# If it shows "self signed certificate" or "unable to verify", proceed with fixes belowOnly proceed if you trust the server and know why it's using a self-signed certificate.
The most secure production-ready solution is to add your custom CA certificate to Node.js's trusted certificate list:
# Save your CA certificate to a file (e.g., ca-cert.pem)
# Then set the environment variable before running Node.js
export NODE_EXTRA_CA_CERTS=/path/to/ca-cert.pem
node your-app.jsOr add it to your start script in package.json:
{
"scripts": {
"start": "NODE_EXTRA_CA_CERTS=./certs/ca-cert.pem node app.js"
}
}This method is safe for production as it explicitly trusts only your specific certificate without disabling all validation.
For programmatic control, provide the CA certificate directly in your HTTPS request configuration:
const https = require('https');
const fs = require('fs');
const options = {
hostname: 'your-server.com',
port: 443,
path: '/api',
method: 'GET',
ca: fs.readFileSync('./path/to/ca-cert.pem')
};
https.request(options, (res) => {
// Handle response
}).end();For libraries like Axios:
const axios = require('axios');
const https = require('https');
const fs = require('fs');
const agent = new https.Agent({
ca: fs.readFileSync('./path/to/ca-cert.pem')
});
axios.get('https://your-server.com/api', { httpsAgent: agent });If intermediate certificates are missing, obtain them from your Certificate Authority and create a complete chain file:
# Concatenate certificates in order: server cert, intermediate(s), root CA
cat server.crt intermediate.crt root.crt > full-chain.pemThen use this file with NODE_EXTRA_CA_CERTS or the ca option in your code.
If the error occurs during npm install with a private registry:
# Set npm to use your CA certificate
npm config set cafile /path/to/ca-cert.pem
# Or for a single install
npm install --cafile=/path/to/ca-cert.pemFor Yarn:
yarn config set cafile /path/to/ca-cert.pemOlder Node.js versions may have outdated CA certificate bundles:
# Check current version
node --version
# Update using nvm (recommended)
nvm install --lts
nvm use --lts
# Or download from nodejs.orgAfter updating, test if the error persists before implementing other fixes.
Why you should NEVER disable certificate validation in production:
While you may see recommendations to use NODE_TLS_REJECT_UNAUTHORIZED=0 or rejectUnauthorized: false, these completely disable certificate validation and expose your application to man-in-the-middle attacks. Never use these in production:
// ❌ NEVER DO THIS IN PRODUCTION
process.env.NODE_TLS_REJECT_UNAUTHORIZED = '0';
// ❌ ALSO NEVER DO THIS
const agent = new https.Agent({ rejectUnauthorized: false });Corporate proxy environments:
If you're behind a corporate proxy that intercepts HTTPS traffic, your company likely provides a custom CA certificate bundle. Contact your IT department to obtain:
- The corporate root CA certificate
- Any intermediate certificates
- Instructions for installing them system-wide or for Node.js
Docker and containerized environments:
When running Node.js in containers, you may need to add CA certificates to the container:
# Copy CA certificate into container
COPY ca-cert.pem /usr/local/share/ca-certificates/company-ca.crt
# Update CA certificates (Debian/Ubuntu)
RUN update-ca-certificates
# Set environment variable for Node.js
ENV NODE_EXTRA_CA_CERTS=/usr/local/share/ca-certificates/company-ca.crtDebugging certificate chains:
Use the --tls-min-v1.0 flag for testing (not production) to see if the issue is TLS version-related:
node --tls-min-v1.0 app.jsInspect certificate chains in detail:
openssl s_client -connect example.com:443 -servername example.com | openssl x509 -textError: EMFILE: too many open files, watch
EMFILE: fs.watch() limit exceeded
Error: Middleware next() called multiple times (next() invoked twice)
Express middleware next() called multiple times
Error: Worker failed to initialize (worker startup error)
Worker failed to initialize in Node.js
Error: EMFILE: too many open files, open 'file.txt'
EMFILE: too many open files
Error: cluster.fork() failed (cannot create child process)
cluster.fork() failed - Cannot create child process