掌握chai測試.catch()塊的正確使用方法
P粉242535777
2023-09-02 12:25:27
<p>我正在努力透過我的程式碼庫的端對端測試來實現良好的覆蓋率,所以我也想測試 <code>.catch()</code> 程式碼。 </p><p>
我的API使用node.js和mongoose。 </p><p>
我使用chai和mocha進行測試。</p>
<p>我嘗試了類似以下的程式碼:</p>
<p><em>檔案 src/controllers/user.controller.js:</em></p>
<pre class="brush:php;toolbar:false;">const User = require("../models/user.model");
const getUser = async(req, res) => {
try {
const user = await User.findOne({name: req.name});
return res.status(200).json(user);
} catch (err) {
// 這是我想要測試的程式碼
console.error(`查找使用者 ${req.name} 時發生錯誤:`, err);
return res.status(err.code).json({ message: err });
}
}</pre>
<p><em>檔案 src/models/user.model.js:</em></p>
<pre class="brush:php;toolbar:false;">const mongoose = require("mongoose");
const UserSchema = mongoose.Schema({
name: {
type: String,
required: "Name is required",
},
});
module.exports = mongoose.model("User", UserSchema);</pre>
<p><em>檔案 test/user.test.js:</em></p>
<pre class="brush:php;toolbar:false;">const chai = require("chai");
const chaiHttp = require("chai-http");
const spies = require("chai-spies");
const User = require("../src/models/user.model");
chai.use(chaiHttp);
chai.use(spies);
chai.should();
describe("應處理mongoose錯誤", function() {
describe("有問題的User.findOne方法", function() {
const _User_findOne_Backup = User.findOne;
beforeEach(function() {
// 這個函數應該要重載真正的findOne函數,但它沒有成功!User.findOne = function() {
return Promise.reject("強制錯誤");
};
});
afterEach(function() { // 每個測試後都恢復真正的函數
User.findOne = _User_findOne_Backup;
});
it("註冊應該回傳伺服器錯誤", function() {
const spy = chai.spy();
return chai
.request(server)
.post("/api/getUser")
.send({name: "Alice"})
.then(spy)
.catch((err) => {
const res = err.response;
res.should.have.status(500);
})
.then(() => {
spy.should.not.have.been.called();
})
;
});
});
});</pre>
<p>問題是在我的測試中,偽造的<code>User.findOne()</code> 方法從未被呼叫:原始的mongoose <code>findOne</code> 方法被呼叫成功,所以<code>getUser</code> 方法從不拋出異常,導致我的測試失敗...</p>
<p>可能我漏掉了一些明顯的東西,但我真的找不到它... :-(</p><p>
如果需要更多的程式碼或上下文,請告訴我...</p>
<p><strong>更新:</strong>
根據 @Bergi 的建議,我添加了關於我的(簡化的)模型和所需模組的完整資訊...</p>
對我來說很好用。
例如:
user.model.js
:user.controller.js
:server.js
:user.test.js
:測試結果:
軟體套件版本: