AngularJs Unit тесты, $httpBackend

borodatych

Постоялец
Регистрация
24 Июн 2016
Сообщения
159
Реакции
105
Здравствуйте.

Задался вопросом тестирования, еле-еле раскурил, но парочку вопросов решить так и не удалось.

Сервис:
Код:
myApp.factory('UserApi', ['$http', function($http) {
    var checkCredentialsUrl = '....';
    return {
        checkCredentials: function(user, pass) {
            return $http({
                method: 'POST',
                data: {
                    jUser: user,
                    jPass: pass
                },
                'headers': {
                    'Content-Type': 'application/x-www-form-urlencoded'
                },
                transformRequest: function(obj) {
                    var str = [];
                    for(var p in obj)
                    str.push(encodeURIComponent(p)+"="+encodeURIComponent(obj[p]));
                    return str.join("&");
                },
                url: checkCredentialsUrl
            });
        }
    }
}]);
Тест:
Код:
describe('UserApi', function () {

    var UserApi, $httpBackend, user, pass, checkCredentialsUrl, succeeded = false;

    beforeEach(module('myApp'));

    beforeEach(inject(function (_UserApi_, _$httpBackend_){
        UserApi = _UserApi_;
        $httpBackend = _$httpBackend_;

        checkCredentialsUrl = '...';
        user = 'qwerty';
        pass = 'qwerty';
    }));

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

    describe('Auth', function () {

        it('CheckCredentials', function () {

            $httpBackend.expectPOST( checkCredentialsUrl, {
                jUser: user,
                jPass: pass
            }, function(headers) {
                return headers['Content-Type'] === 'application/x-www-form-urlencoded';
            }).respond(200);

            UserApi.checkCredentials(user, pass).then(function(response){
                succeeded = true;
            });

            $httpBackend.flush();

            expect(succeeded).toBe(true);
        });
    });

});

Тест падает с ошибкой:
Код:
SyntaxError: Unexpected token j in JSON at position 0
    at Object.parse (native)
    at Object.fromJson (node_modules/angular/angular.js:1333:14)
    at MockHttpExpectation.matchData (node_modules/angular-mocks/angular-mocks.js:1928:77)
    at $httpBackend (node_modules/angular-mocks/angular-mocks.js:1384:24)
    at sendReq (node_modules/angular/angular.js:11776:9)
    at serverRequest (node_modules/angular/angular.js:11571:16)
    at processQueue (node_modules/angular/angular.js:16383:28)
    at node_modules/angular/angular.js:16399:27
    at Scope.$eval (node_modules/angular/angular.js:17682:28)
    at Scope.$digest (node_modules/angular/angular.js:17495:31)
     Error: [$rootScope:inprog] $digest already in progress
http://errors.angularjs.org/1.5.8/$rootScope/inprog?p0=%24digest
    at node_modules/angular/angular.js:68:12
    at beginPhase (node_modules/angular/angular.js:18042:15)
    at Scope.$digest (node_modules/angular/angular.js:17472:9)
    at Function.$httpBackend.verifyNoOutstandingExpectation (node_modules/angular-mocks/angular-mocks.js:1830:38)
    at Object.<anonymous> (tests/controllers/auth.test.js:19:22)

Если убрать из сервиса секцию transformRequest то тест отрабатывает.
Подскажите как прикрутить transformRequest к $httpBackend?


Сейчас я просто использую, пока смотрю:
Код:
.respond(200)
Этого мало, и можно вот так:
Код:
.respond(function(method, url, data, headers, params) {
    // for requested url of '/user/1234' params is {id: '1234'}
  });
(c) Для просмотра ссылки Войди или Зарегистрируйся
Но что если у меня нет доступа в backend и ни кто не дает метод, который на сервере обрабатывает запрос?!
Можно ли в тестах просто сделать запрос на удаленный сервер, получить ответ, обработать его и на основе данных уже вываливать ошибку или нет?
 
Как ни странно, но достаточно, заменить:
Код:
$httpBackend.expectPOST( checkCredentialsUrl, {
    jUser: user,
    jPass: pass
}, function(headers) {
    return headers['Content-Type'] === 'application/x-www-form-urlencoded';
}).respond(200);

На:
Код:
var data = {
    jUser: user,
    jPass: pass
};
$httpBackend.expectPOST( checkCredentialsUrl, function (data) {
    return data;
}, function(headers) {
    return headers['Content-Type'] === 'application/x-www-form-urlencoded';
}).respond(200);

Причину разбирать не стал, тест завелся.
Если кто пояснит, буду признателен.

Остался второй вопрос.
Если у кого есть хотя бы мысли или доводы, даже бредовые, тоже будет полезным, может натолкнуть на мысль.

Спасибо.
 
Здравсвуйте, посоветуйте пожалуйста unit testing framework для angular 2
 
Назад
Сверху