我有一段情绪化的时间试图使用护照的JWT策略测试受保护的路线,并使用授权标题。
我已经尝试过axios,supertest,superagent,我也得到同样的错误 - ' socket挂断':
Error: socket hang up
at createHangUpError (_http_client.js:253:15)
at Socket.socketOnEnd (_http_client.js:345:23)
at emitNone (events.js:91:20)
at Socket.emit (events.js:185:7)
at endReadableNT (_stream_readable.js:974:12)
at _combinedTickCallback (internal/process/next_tick.js:74:11)
at process._tickDomainCallback (internal/process/next_tick.js:122:9) code: 'ECONNRESET', response: undefined }
这在开发环境中非常有效,这只发生在测试环境中 - 单元测试或dev env指向测试数据库/用户。
我知道这个错误意味着连接因服务器崩溃或语法错误而关闭,但是没有语法错误。端点没有通过护照身份验证:
passport.authenticate('jwt'...
为什么呢?怎么解决这个问题?
终点:
router.route('/private')
.get(
passport.authenticate('jwt', { session: false }), (req, res, next) => {
res.json({ allTheThings: true });
})
测试:
describe('GET /api/private', () => {
it('should work', () => {
const USER_JWT_VALID = 'JWT asdf.....';
let instance = axios.create();
instance.defaults.headers.common['Authorization'] = USER_JWT_VALID;
return instance.get('http://localhost:3000/api/private')
.then((response) => {
expect(response.data).to.be.an('object'); // response.data undefined
}).catch((error) => {
console.log('err ', error); //socket hang up
});
});
});
如果我删除passport.authenticate
并只是发送一个json响应,它会按预期工作。
日志显示请求与Authorization标头中的正确JWT一起发送。
RE评论
我有一个不同的开发和测试用户/用户。使用dev中的测试数据库,我能够复制单元测试中出现的问题。如果我排除授权标题,正如预期的那样,我会得到一个未经授权的#39;响应(来自令牌检查功能)。
一旦我向JWT添加授权标题,我就不会得到任何回复:(
进一步调试
在测试环境中,如果有授权标头,我的api似乎无法再执行任何GET请求。没有标题,一切正常。我怀疑这与最近的一些依赖更新有关。
答案 0 :(得分:0)
为测试环境创建一个全新的用户并在单元测试中使用它之后,一切都按预期工作。使用授权标头中的用户JWT的GET请求可以完美地工作。
似乎在测试环境(来自mongo db)中用于身份验证的用户以某种方式使用了无效的JWT。可能与基于用户架构构建JWT的方式有关。
我不知道为什么或如何发生这种情况(早期构建阶段)。现在无法复制。
我的单元测试正在执行以下操作:
1)POST到身份验证端点以获取JWT令牌(来自用户电子邮件和密码)
2)使用该JWT获取仅具有私有身份验证的端点。
在私人GET上,passport.authenticate('jwt' ....
根本就没有工作,因此没有请求或回复。
除了无效的JWT之外,我看不出任何其他原因。
我从中了解到,如果您在进行身份验证时遇到失败的单元测试,请排除旧用户/新用户并从中进行操作。