问题现象:反复出现的OIDC认证失败
许多开发者在配置GitHub Actions的NPM可信发布(OIDC认证)时,都会遇到一个顽固的问题:
npm notice Access token expired or revoked. Please try logging in again.
尽管按照官方文档正确配置了OIDC trust relationship,这个404错误依然反复出现。
根本原因:Node版本与NPM兼容性
根据npm/cli#8816的讨论,问题的核心在于:
Node.js 25以下版本自带的npm版本过旧,不支持完整的OIDC实现!
版本兼容性矩阵
| Node版本 | 自带npm版本 | OIDC支持 |
|---|---|---|
| Node 25+ | npm 10+ | ✅ 完全支持 |
| Node 20 | npm 9.x | ⚠️ 部分支持(可能失败) |
| Node 18 | npm 8.x | ❌ 不支持 |
| Node 16 | npm 7.x | ❌ 不支持 |
解决方案一:升级Node版本(推荐)
最简单直接的解决方案是升级你的GitHub Actions工作流中的Node版本:
# .github/workflows/publish.yml
name: Publish to NPM
on:
release:
types: [published]
jobs:
publish:
runs-on: ubuntu-latest
permissions:
id-token: write # OIDC必需
contents: read
steps:
- uses: actions/checkout@v4
- name: Setup Node.js
uses: actions/setup-node@v4
with:
# 关键:使用Node 25或更高版本
node-version: '25.x'
registry-url: 'https://registry.npmjs.org/'
- run: npm ci
- run: npm test
- name: Publish to NPM
run: npm publish --provenance --access public
env:
NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} # 传统token作为后备
解决方案二:升级NPM版本(兼容旧Node)
如果你因项目限制必须使用旧版Node,可以在工作流中显式升级npm:
name: Publish to NPM with OIDC
on:
release:
types: [published]
jobs:
publish:
runs-on: ubuntu-latest
permissions:
id-token: write # 必需:获取OIDC令牌
contents: read
steps:
- uses: actions/checkout@v4
- name: Setup Node.js (旧版本)
uses: actions/setup-node@v4
with:
# 使用旧版Node(如Node 18)
node-version: '18.x'
registry-url: 'https://registry.npmjs.org/'
# 关键步骤:强制升级到npm 10+
- name: Upgrade npm to latest
run: |
# 查看当前npm版本
npm --version
# 升级到支持OIDC的最新版本
npm install -g npm@latest
# 验证升级后的版本
npm --version
- run: npm ci
- run: npm test
- name: Publish with OIDC
run: |
# 确保使用正确的npm版本
npm --version
# 使用--provenance启用可信发布
npm publish --provenance --access public
完整的最佳实践配置
1. 正确的OIDC权限配置
在组织或仓库设置中启用正确的权限:
# 工作流文件必须包含这些权限
permissions:
id-token: write # OIDC令牌获取
contents: read # 代码仓库访问
2. 双重认证策略
为防万一,可以同时配置OIDC和传统token:
- name: Publish with fallback strategy
run: |
# 尝试OIDC发布
if npm publish --provenance --access public; then
echo "OIDC发布成功"
else
echo "OIDC失败,尝试传统token发布"
echo "//registry.npmjs.org/:_authToken=${{ secrets.NPM_TOKEN }}" > .npmrc
npm publish --access public
fi
3. 版本检查和验证步骤
在发布前添加验证步骤:
- name: Verify OIDC readiness
run: |
echo "Node版本: $(node --version)"
echo "NPM版本: $(npm --version)"
# 检查npm是否支持provenance
npm config get provenance || echo "检查provenance支持"
# 验证GitHub Actions环境
if [ -n "$GITHUB_ACTIONS" ]; then
echo "运行在GitHub Actions环境中"
fi
常见错误排查清单
❌ 错误配置
- 缺少
id-token: write权限 - Node版本低于25且未升级npm
- npm版本低于10.0.0
- 未启用仓库的"读取和写入权限"
✅ 正确配置检查点
- [x]
permissions中包含id-token: write - [x] Node版本≥25 或 npm版本≥10
- [x] 使用
actions/setup-node@v4或更高版本 - [x]
npm publish命令包含--provenance标志 - [x] NPM包设置中启用了"要求双重认证"
为什么需要OIDC?
传统NPM_TOKEN方式的安全问题:
- 令牌可能长期有效
- 可能被意外泄露
- 权限范围可能过大
OIDC优势:
- 短期令牌(几分钟有效期)
- 自动令牌轮换
- 细粒度权限控制
- 发布来源可验证(provenance)
总结
NPM OIDC认证的404错误通常不是配置问题,而是版本兼容性问题。记住这个简单的规则:
使用Node 25+,或者手动升级npm到10+
这个问题的隐蔽性在于:错误信息没有明确指出是版本问题,而是提示token过期或撤销,导致开发者花费大量时间检查权限配置而不是检查工具版本。
通过确保正确的版本组合,你可以顺利实现NPM的可信发布,享受OIDC带来的安全优势,同时避免令人沮丧的404错误。



最新评论