Ошибка Qunit: утверждение вне контекста тестирования
Я искал все, и эта ошибка возникает из-за неправильного использования asyncTest
. Однако, по документации, похоже, что я делаю это правильно. Я предполагаю, что мне где-то не хватает маленькой детали, и мне нужна дополнительная пара глаз...
Я пытаюсь проверить код, который делает запрос ajax для получения страницы, а затем загружает ее в лайтбокс. lightbox-content
не отображается в DOM до тех пор, пока вызов ajax не завершится и не будет отображаться. Поэтому я могу проверить это только в моем обратном вызове onComplete, где у меня есть мой тест, чтобы проверить, правильно ли он загружен.
Вот мой код:
asyncTest('mytest', 1, function() {
utils.lightbox.show('/login', {
onComplete: function() {
ok($('#lighbox-content').is(':visible'), 'Lightbox loaded the /login page.');
start();
}
});
});
Я получаю сообщение об ошибке:
Uncaught Error: assertion outside test context, was at HTMLDivElement.window.utils
Кто-нибудь может увидеть, где я ошибаюсь?
Ответы
Ответ 1
Я согласен с тем, что ваш код соответствует документации, насколько я могу судить.
Обновление
Несмотря на то, что документация не показывает его, я задаюсь вопросом, нужно ли вам указывать QUnit для остановки в какой-то момент, чтобы он знал, что ждать после возвращения тестовой функции. Я бы подумал, что QUnit предполагает это, так как это асинхронный тест, но это стоит того.
asyncTest('mytest', 1, function() {
stop();
...
});
Я использую Sinon.JS, чтобы избежать вызовов AJAX в первую очередь. Это имеет три преимущества:
- Я не зависеть от сервера для ответа на запросы.
- Я могу указать разные результаты для каждого теста.
- Тесты выполняются намного быстрее.
Мытье может быть сделано на уровне XMLHttpRequest или в методе jQuery, и это довольно просто. Вот пример из одного из моих тестов:
module("geo", {
setup: function () {
this.server = sinon.fakeServer.create();
},
teardown: function () {
this.server.restore();
}
}
test("returns detected ZIP code", function () {
this.server.respondWith("/geo/detect-zip-from-ip",
[ 200, { "Content-Type": "text/html" }, '90210' ]);
geo.detectZip(function (zip) {
assertThat(zip, is('90210'));
});
this.server.respond();
});
Ответ 2
Я нашел решение для своего случая, надеюсь, что ваша проблема имеет тот же источник.
Объяснение словами:
- У меня сложный асинхронный тест
- У меня есть задержки событий, и есть
ok
и equal
утверждения внутри
- Конечно, все это завернуто внутри
asyncTest
- Но, когда тест "завершен", и я вызываю
start()
, обработчики событий остаются там
- После вызова
start()
все дальнейшие вызовы ok
внутри asyncTest
становятся незаконными
- И выбросить исключения
- Интересно, что произойдет, если превышено число в
expect
(в вашем примере это второй параметр). Такое же исключение?
Объяснение в коде:
asyncTest('mytest', /*1,*/ function() {
function imgLoadedOrFailed (result) {
clearTimeout(imageTimeToLive);
img.off();
ok(result, 'Image in carousel pane has been loaded');
}
var imageTimeToLive = setTimeout(
imgLoadedOrFailed.bind(this, false),
5000),
img = panes[index].find('img:first');
if (img) {
img.on('load', imgLoadedOrFailed.bind(this, true));
img.on('error', imgLoadedOrFailed.bind(this, false));
}
});
// at some point I call: start();
В этом примере, когда я "закончу" вызов вызова start()
, события onload
и onerror
все равно могут произойти.