← 中文资源

简体中文版本

Node.js error:0308010C 数字信封算法不受支持错误排查

把 error:0308010C digital envelope routines::unsupported 映射到 OpenSSL 3 移除 md4 的事实,再升级工具链或审慎启用 legacy provider。

阅读英文原文

症状

  那串十六进制错误码其实指向一个具体决定:0308010C 表示 provider 层拒绝了请求的摘要算法。在 Node 18 上一行代码即可复现:require(‘crypto’).createHash(‘md4’) 抛出同样的 error:0308010C:digital envelope routines::unsupported,而同一行在 Node 16 上成功。这一对版本就是全部故事:OpenSSL 3 把 md4 移出默认 provider,而装着的 webpack 4 用 md4 算缓存摘要。堆栈通常落在 webpack/lib/util/createHash.js,同时点名了受害者与算法。源码一行未改、CI 换了 Node 镜像、本地还停在 16——于是“只在 CI 挂”。

诊断思路

  先用裸 createHash 调用复现错误,证明是运行时加密策略而非打包器逻辑问题;再跨版本对照(17+ 失败、16 成功)钉死 OpenSSL 3 迁移这条线;最后在 node_modules 里 grep md4,确认是哪个依赖层在消费该算法,从而决定升级哪个包。

根因

  Node 17 起捆绑 OpenSSL 3,将 md4 等遗留算法移出默认 provider。构建工具用 md4 计算完整性哈希,createHash 抛出 error:0308010C,因为不启用 legacy provider 该算法不可用。回归随运行时升级而来,与任何代码变更无关。

修复与验证

  优先升级工具链:webpack 5、vue-cli 5、react-scripts 5 都已改用 xxhash64 或 md5 兜底,这是持久解。升级暂时不可行时,把 NODE_OPTIONS=–openssl-legacy-provider 作为只作用于构建步骤的临时方案写进 build script,并配上落日计划。注意该标志会为整个进程重新启用已废弃且未经验证的加密路径:绝不能设成镜像全局变量,绝不能用于生产服务器,并加一个定期“无标志构建”的 CI 哨兵,让兜底无法悄悄变成永久。验证时升级后在不带任何 NODE_OPTIONS 的情况下跑生产构建,两次连续构建的输出哈希应稳定一致;若兜底仍在,全仓 grep 该标志,只允许出现在构建脚本里,且每处都标注移除日期,升级落地当天让无标志 CI 亮红收尾。

代码示例

Error: error:0308010C:digital envelope routines::unsupported
    at new Hash (node:internal/crypto/hash:71:19)
node -e "require('crypto').createHash('md4')"
# throws error:0308010C ... unsupported
node -e "require('crypto').createHash('md4')" 2>/dev/null && echo ok || echo affected
{
  "scripts": {
    "build": "NODE_OPTIONS=--openssl-legacy-provider webpack --mode production"
  }
}