我的问题是(看似)事情超出范围,或者当我在下面的函数中输入catch
块时,范围被污染了:
export const getOne = model => async (req, res, next) => {
let id = req.params.id
let userId = req.user
try {
let item = await model.findOne({ _id: id, createdBy: userId }).exec()
if (!item) {
throw new Error('Item not found!')
} else {
res.status(200).json({ data: item }) // works perfectly
}
} catch (e) {
res.status(400).json({ error: e }) // TypeError: res.status(...).json is not a function
// also TypeError: next is not a function
// next(e)
}
}
足够有趣的是,在res.status(...).end()
块中使用catch
可以很好地工作,但是令我感到困扰的是我无法将任何详细信息发送回响应。根据{{3}}和res.send()
的“快速文档”,我应该能够链接到.status()
,这也很有趣,在上述try
语句中,如果一切都成功了-res.status(200).json(...)
运作完美。
我还尝试将错误处理抽象到中间件res.json
,并通过闭包,我仍然应该可以在next
语句中访问catch
,对吗?为什么返回的不是函数?
res.status(...).json(...)
在我的try
而不是catch
块中起作用?next
不再是catch
块中的函数?谢谢!
这在单元测试中失败,以下代码会产生上述错误:
describe('getOne', async () => {
// this test passes
test('finds by authenticated user and id', async () => {
expect.assertions(2)
const user = mongoose.Types.ObjectId()
const list = await List.create({ name: 'list', createdBy: user })
const req = {
params: {
id: list._id
},
user: {
_id: user
}
}
const res = {
status(status) {
expect(status).toBe(200)
return this
},
json(result) {
expect(result.data._id.toString()).toBe(list._id.toString())
}
}
await getOne(List)(req, res)
})
// this test fails
test('400 if no doc was found', async () => {
expect.assertions(2)
const user = mongoose.Types.ObjectId()
const req = {
params: {
id: mongoose.Types.ObjectId()
},
user: {
_id: user
}
}
const res = {
status(status) {
expect(status).toBe(400)
return this
},
end() {
expect(true).toBe(true)
}
}
await getOne(List)(req, res)
})
})
答案 0 :(得分:1)
为什么res.status(...)。json(...)可以在我的try中工作但不能捕获块?
似乎您正在传递使用单元测试运行时仅具有status
和end
方法的非表达对象。这就是为什么它找不到json
方法