为什么我要在单元测试中模拟HTTP请求?

时间:2014-06-13 00:11:24

标签: javascript angularjs unit-testing jasmine

我正在开展一个项目,我们已经开始编写Jasmine单元测试了。像任何优秀的JS应用程序一样,这个应用程序会进行大量的异步数据提取。我看到angular提供了$ httpBackend来模拟HTTP请求。我也读过并听说在控制器中测试AJAX请求是一个坏主意,因此存在$ httpBackend的存在理由。为什么测试AJAX调用不是一个好主意?大型JS应用程序如何解决这个问题? 什么时候实际测试击中实际服务器?

2 个答案:

答案 0 :(得分:3)

断言你不应该从Jasmine测试服务器是一个过于简单的概括。无论您是想要小型测试,大型测试,还是两者的某种组合,都取决于应用程序。有人可能会说它不是一个"单位"再试一次 - 它是一个"整合"测试 - 但这些术语已经超载到废话,因为它是一个相当人为的二分法。编写有用且可维护的测试。选择测试的大小是其中的一个重要部分。适当的大小需要您自己判断情况。

答案 1 :(得分:1)

单元测试的想法是概述应用程序的一小部分应该如何工作。如果它通过了该测试,您就知道它的运行符合规定。

如果要测试向API发送请求的服务,请设置单元测试,检查传出请求的位置/内容/是否存在,并验证它是否正确响应了有效响应。为了使测试尽可能具体,它不应该测试那个小泡沫之外的任何东西。

假设我们要测试此PersonService角度服务:

app.service('PersonService', function ($q, $timeout, $http) {
    this.addPerson = function(data) {
        var deferred = $q.defer();
        $http.post('api/People', data).then(function(response) {
            deferred.resolve(response);
        });
        return deferred.promise;
    };
});

这是一个简单的Jasmine测试:

var service, $httpBackend;
beforeEach(module('app'));
beforeEach(inject(function(_PersonService_, _$httpBackend_) {
    service = _PersonService_;
    $httpBackend = _$httpBackend_;
}));

describe('addPerson', function() {
    var person;
    beforeEach(function() {
        // Make a person to send
        person = new Person({ id: "0ff1165f-7f75-45ed-8faa-ee94d874a1cf" });
    });

    afterEach(function() {
        $httpBackend.verifyNoOutstandingExpectation();
        $httpBackend.verifyNoOutstandingRequest();
    });

    it('should send a person object to the API', function() {
        // setup
        var promise, expected, actual;
        expected = /* Whatever is sent back */
        $httpBackend.whenPOST('api/People', person)
            .respond(expected);

        // act
        promise = service.addPerson(person);
        promise.then(function(response) {
            actual = response.data;
        });

        $httpBackend.flush();

        // assert
        expect(actual).toEqual(expected);
    });
});

所以我们有一个测试来检查这个非常基本的功能(无论API实际上做了什么)。这允许我们单独测试代码的各个部分 - 即如果API被破坏,除了相关的API测试之外,您的PersonService测试不会中断。

要构建以确保一切正常工作的是集成测试