1

我有一个调用 JSON 的函数,然后在成功函数中对 DOM 进行一些更改。我试图在我的 Jasmine 测试中使用mock-ajax 库,以避免不得不公开各种私有函数进行模拟。

即使在单步执行测试时request.response设置了 onSuccess 方法,也不会被调用。

我的测试:

 describe('the table loader', function () {
        var request;

        beforeEach(function() {
            //html with a loader div, an output div and a transit and dwell template
            setFixtures('<div class="loader"></div><div class="row"><div id="output" class="col-xs-12"></div></div><script id="thingTemplate" type="text/x-handlebars">{{snip}}</script>');
            expect($('.loader')).toBeVisible();

            //start ajax call
            window.dashboards.thing.display({
                loaderId: '.loader',
                templateId: '#thingTemplate',
                templateOutletId: '#output',
                dataUrl: '/my/fake/url'
            });
            //catch the ajax request
            request = mostRecentAjaxRequest();
        });

        describe('on success', function () {
            beforeEach(function() {
                //populate the response
                request.response({
                    status: 200,
                    responseText: "{rowItem: [{},{},{}]}"
                });
            });

            it('should hide the loader', function () {
                //thing should now receive that JSON and act accordingly
                expect($('.loader')).not.toBeVisible();
            });
        });
    });

和我的代码:

(function (dashboards, $) {
    dashboards.thing = dashboards.thing || {};

    var compileTable = function(templateId, jsonContext) {
        var source = $(templateId).html();
        var template = Handlebars.compile(source);
        var context = jsonContext;
        return template(context);
    };

    var getDashboardData = function(options) {
        $.getJSON(
            options.dataUrl,
            function (data) {
                processDashboardData(options, data);
            }
        ).fail(function (jqxhr, textStatus, error) {
            console.log('error downloading dashboard data');
            console.log(textStatus + ': ' + error);
        }).always(function() {
            console.log('complete');
        });
    };

    var processDashboardData = function (options, data) {
        $(options.loaderId).hide();
        $(options.templateOutletId).html(compileTable(options.templateId, data));
    };

    dashboards.thing.display = function (options) {
        getDashboardData(options);
    };
}(
    window.dashboards = window.dashboards || {},
    jQuery
));

没有调用任何延迟函数(成功、错误和始终)。

编辑

基于下面@gregg 的回答(他是对的,我没有在示例代码中包含 UseMock 调用),这感觉像是一个版本问题。即使包括了那个电话,这仍然对我不起作用。

在 github 上添加了一个可运行的示例

4

3 回答 3

1

因此,截至 2014 年 1 月 29 日,Github 上 1.3.1 标记中的 mock-ajax 自述文件中的下载链接并未指向文件的正确版本。

从标签的 lib 文件夹手动下载 mock-ajax 文件确实有效。

换句话说,对于 1.3.1 标记版本,不要直接从 tag lib 文件夹下载自述文件链接下载

于 2014-01-29T09:14:17.680 回答
1

您需要确保jasmine.Ajax.useMock()在实际进行调用之前安装 ajax 模拟,否则 jasmine-ajax 不会接管 XHR 对象,您将发出真正的请求。一旦我对您的示例代码执行此操作,看起来responseText您发送的不是 JSON 可解析的并且 jQuery 爆炸了。但我仍然看到控制台中记录了“完整”消息。

于 2014-01-26T21:54:00.963 回答
0

您的 ajax 调用和 jasmine 返回的数据格式可能不同——我相信这会引发无法恢复的异常,因此您的回调函数都没有运行。

较新版本的 jasmine-ajax 也使用request.respondWith,而且值得注意的是(虽然我认为 jQuery 处理了这个),Jasmine 没有XMLHttpRequest.Done定义,所以如果你使用 vanilla JS,你必须自己处理这种情况。最后我使用jasmine.Ajax.install()而不是jasmine.Ajax.useMock().

唷——很难知道究竟该怎么做,因为 Jasmine 对旧版本的文档太差了,而且它们之间有很多不一致之处。

于 2015-04-28T20:53:17.950 回答