[解決済み] Chaiを非同期Mochaテストで動作させる方法はありますか?
2023-07-08 10:46:11
質問
ブラウザランナーを使ってMochaでいくつかの非同期テストを実行していますが、Chaiのexpectスタイルのアサーションを使おうとしています。
window.expect = chai.expect;
describe('my test', function() {
it('should do something', function (done) {
setTimeout(function () {
expect(true).to.equal(false);
}, 100);
}
}
これは通常のアサーション失敗のメッセージは出さず、代わりに
Error: the string "Uncaught AssertionError: expected true to equal false" was thrown, throw an Error :)
at Runner.fail (http://localhost:8000/tests/integration/mocha/vendor/mocha.js:3475:11)
at Runner.uncaught (http://localhost:8000/tests/integration/mocha/vendor/mocha.js:3748:8)
at uncaught (http://localhost:8000/tests/integration/mocha/vendor/mocha.js:3778:10)
というわけで、明らかにエラーをキャッチしているのですが、ただ正しく表示されていません。これを行う方法について何かアイデアはありますか?私はエラーオブジェクトで "done" を呼び出すことができると思いますが、そうすると Chai のようなエレガントさが失われ、非常に不格好になります...。
どのように解決するのですか?
非同期テストで例外が発生し、失敗すると
expect()
で捕捉できない例外が発生します。
it()
の外で例外が発生するため
it()
のスコープ外で投げられたからです。
表示されているキャプチャされた例外は
process.on('uncaughtException')
を使うか
window.onerror()
を使ってください。
この問題を解決するためには、以下のようにして呼び出された非同期関数内で例外を捕捉する必要があります。
setTimeout()
を呼び出すために
done()
を呼び出すために、最初のパラメータとして例外を指定します。また
done()
を呼び出す必要があります。そうしないと、テスト関数が完了したことを通知しないので、mochaはタイムアウトエラーを報告します。
window.expect = chai.expect;
describe( 'my test', function() {
it( 'should do something', function ( done ) {
// done() is provided by it() to indicate asynchronous completion
// call done() with no parameter to indicate that it() is done() and successful
// or with an error to indicate that it() failed
setTimeout( function () {
// Called from the event loop, not it()
// So only the event loop could capture uncaught exceptions from here
try {
expect( true ).to.equal( false );
done(); // success: call done with no parameter to indicate that it() is done()
} catch( e ) {
done( e ); // failure: call done with an error Object to indicate that it() failed
}
}, 100 );
// returns immediately after setting timeout
// so it() can no longer catch exception happening asynchronously
}
}
すべてのテストケースでこれを行うのは面倒ですし、DRYではないので、これを行うための関数を提供したいと思うかもしれません。この関数を
check()
:
function check( done, f ) {
try {
f();
done();
} catch( e ) {
done( e );
}
}
とは
check()
を使えば、非同期テストを以下のように書き換えることができます。
window.expect = chai.expect;
describe( 'my test', function() {
it( 'should do something', function( done ) {
setTimeout( function () {
check( done, function() {
expect( true ).to.equal( false );
} );
}, 100 );
}
}
関連
-
[解決済み] JavaScriptで現在のURLを取得する?
-
[解決済み] jQueryで現在のURLを取得する?
-
[解決済み] jQueryでJavaScriptオブジェクトから選択する際に、オプションを追加する最も良い方法は何ですか?
-
[解決済み] どうすればjQueryに非同期ではなく、同期のAjaxリクエストを実行させることができますか?
-
[解決済み] Mochaで単一のテストを実行するには?
-
[解決済み] Mocha によるコードカバレッジ
-
[解決済み】Mocha / Chai expect.to.throwがスローエラーをキャッチしない
-
[解決済み] アサインの左側にJavascriptのオブジェクトブラケット表記({ ナビゲーション } =)があります。
-
[解決済み] Node.jsのES6クラスをrequireで作る
-
[解決済み] JavaScriptデータフォーマット/プリティプリンタ
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み] JSのDateからDay名
-
[解決済み] bootstrap のポップオーバーがすべての要素の上に表示されない
-
[解決済み] アサインの左側にJavascriptのオブジェクトブラケット表記({ ナビゲーション } =)があります。
-
[解決済み] Reactコンポーネントでthis.setStateを複数回使用するとどうなりますか?
-
[解決済み] javascript includes() 大文字小文字を区別しない
-
[解決済み] Javascriptで動的に命名されたメソッドを呼び出すにはどうすればよいですか?
-
[解決済み] jqueryはjavascriptのライブラリなのかフレームワークなのか?[クローズド]
-
[解決済み] querySelectorAllがない場合、ライブラリを使用せずに属性で要素を取得する?
-
[解決済み] JavaScriptの文字列プリミティブとStringオブジェクトの違いは何ですか?
-
[解決済み] リダイレクトされずにHTMLフォームを送信する方法