Node/Express解码JWT时遇PEM routines错误的求助
解决JWT认证中的
PEM routines:PEM_read_bio:no start line错误 这个PEM相关的错误我之前也碰到过,大概率是密钥文件格式问题、路径错误或者加密算法不匹配导致的,咱们一步步来排查解决:
1. 先排查PEM文件本身的问题
这个错误最常见的原因是你读取的PEM文件不符合标准格式,或者路径不对:
- 检查
key.pem和server.crt是否在项目根目录下(你用的是./key.pem相对路径),如果文件不存在,读取到的是空内容,就会触发这个错误。 - 打开这两个文件,确认格式是否正确:
- 私钥
key.pem必须以-----BEGIN PRIVATE KEY-----开头,以-----END PRIVATE KEY-----结尾,中间是Base64编码的密钥内容,不能有多余的空格或换行。 - 证书
server.crt必须以-----BEGIN CERTIFICATE-----开头,对应结尾,内容格式也要合规。
- 私钥
2. 检查JWT加密算法的匹配性
看你的代码,你同时引入了对称加密的用法(用字符串'your secret here'解密)和非对称加密的PEM文件,但没对应上:
- 如果你的JWT是用**对称算法(比如HS256)**生成的:
那你不需要读取PEM文件,直接确保解密用的密钥和生成JWT的密钥完全一致即可。可以删掉代码中读取key.pem和server.crt的冗余代码,避免混淆。 - 如果你的JWT是用**非对称算法(比如RS256)**生成的:
那你需要用公钥(通常是server.crt)来解密,而不是字符串密钥,并且要指定算法。修改你的解密代码:const publicKey = fs.readFileSync('./server.crt', 'utf8'); let token = req.headers.authorization.split(' ')[1]; // 第三个参数设为true表示验证签名,第四个参数指定算法 var decoded = jwt.decode(token, publicKey, true, 'RS256');
3. 用express-jwt简化认证逻辑
你已经引入了express-jwt但没使用,其实它可以帮你简化中间件逻辑,避免手动处理解码和错误:
- 对称加密场景:
app.use(jwtToken({ secret: 'your secret here', algorithms: ['HS256'] }).unless({ path: ['/login'] })); // 排除不需要认证的接口,比如登录 - 非对称加密场景:
const publicKey = fs.readFileSync('./server.crt', 'utf8'); app.use(jwtToken({ secret: publicKey, algorithms: ['RS256'] }).unless({ path: ['/login'] }));
额外注意点
你的代码里定义了options对象但没用到,这应该是之前HTTPS服务器的残留代码。如果需要启动HTTPS服务器,应该替换app.listen为:
const https = require('https'); https.createServer(options, app).listen(port, () => { console.log('HTTPS server started on port 3000'); });
如果不需要HTTPS,直接删掉options相关代码即可。
内容的提问来源于stack exchange,提问作者userlkjsflkdsvm
相关产品推荐
相关产品推荐

