NodeJS+Express本地发SendGrid邮件报UNABLE_TO_GET_ISSUER_CERT_LOCALLY错
问题根因
你碰到的UNABLE_TO_GET_ISSUER_CERT_LOCALLY错误,本质是Node.js进程和SendGrid SMTP服务器建立TLS连接时,在本地可信CA证书库中找不到对端服务证书的签发根证书,TLS握手直接失败。
你之前执行的所有npm相关配置操作全是无效操作——npm set strict-ssl=false、修改npm registry、设置npm的cafile,这些配置只对npm包管理器本身生效,管的是你执行npm install拉取依赖包时的SSL校验规则,和你业务代码运行时建立SMTP连接的TLS逻辑没有任何关系,这也是你做了一堆配置还是报错的核心原因。
核心问题解答
1. 发送邮件是否必须配置CA证书?
- 公网环境对接官方SendGrid SMTP服务不需要手动配置CA证书。Node.js默认内置了Mozilla维护的全量可信根证书库,只要你的Node版本不是过于老旧、本地系统证书库没有被篡改,默认就能正常完成证书校验。
- 只有两种场景需要手动配置CA:一是你处于企业内网环境,出口防火墙/代理做了TLS中间人解密,替换了公网服务的证书;二是你对接的是私有部署的邮件服务,使用了自签名证书。
2. 报错修复方案
按优先级从高到低尝试,优先选生产可用的方案:
生产环境可用方案
- 先检查SMTP连接配置是否正确:SendGrid官方SMTP地址为
smtp.sendgrid.net,优先使用465端口(隐式TLS),其次选587端口(STARTTLS),不要写错域名、不要直接用IP地址连接。 - 升级Node.js到官方维护的LTS版本(建议18.x、20.x及以上),过旧的Node版本内置的根证书库没有更新,无法识别SendGrid当前使用的DigiCert根证书,会直接校验失败。
- 如果是公司内网环境,直接找运维索要内网TLS代理的根证书,不要自行从公网下载零散的DigiCert根证书——内网代理会替换所有站点的证书,公网根证书无法通过校验。
本地开发临时调试方案(禁止用于生产)
如果只是本地localhost环境调试,不想折腾证书逻辑,可以在初始化邮件发送实例(比如nodemailer)时,给TLS配置添加rejectUnauthorized: false跳过证书校验,示例代码:
const nodemailer = require('nodemailer') const transporter = nodemailer.createTransport({ host: 'smtp.sendgrid.net', port: 465, secure: true, auth: { user: 'apikey', pass: '你的SendGrid API密钥' }, tls: { rejectUnauthorized: false } })
注意:该配置会关闭当前连接的证书校验,存在中间人攻击风险,绝对不能在生产环境开启。
需要手动指定证书的场景
如果确实需要手动加载可信CA,不要零散加载单个根证书,直接使用全量可信根证书包:
- 安装依赖:
npm install ca-certificates - 在邮件实例的TLS配置中传入全量CA证书,内网环境需要额外追加企业自签根证书即可,示例:
const caList = require('ca-certificates') // 如果是内网,把企业根证书的PEM内容push到caList数组里即可 const transporter = nodemailer.createTransport({ host: 'smtp.sendgrid.net', port: 465, secure: true, auth: { user: 'apikey', pass: '你的SendGrid API密钥' }, tls: { ca: caList } })
3. Node.js环境正确配置证书的方式
- 单服务/单连接配置(推荐):给具体的TLS连接(发邮件、调用第三方接口、连接数据库)单独传入
tls.ca参数指定可信证书,仅影响当前连接,不会污染全局配置。 - 全局配置(不推荐):启动Node服务时通过
NODE_EXTRA_CA_CERTS环境变量指定额外的可信证书路径,比如NODE_EXTRA_CA_CERTS=/path/to/your/extra-ca.pem node app.js,该配置会给当前启动的Node进程追加可信根证书,不会覆盖Node默认内置的证书库。 - 避坑提醒:不要用
npm config set cafile这类npm配置命令设置业务服务的证书,该配置仅对npm本身生效,对业务代码没有任何作用。
内容的提问来源于stack exchange,提问作者Salim
相关产品推荐
相关产品推荐

