Тестирование угловой директивы, которая удаляет элемент dom, не работает (по крайней мере, для меня)

У меня есть директива, которая удаляет элемент dom после некоторой проверки разрешений:

angular.module('app').directive('permissionNeeded', function ($location, $route, SecurityService) {
    return {
        restrict: 'A',
        link: function (scope, element, attributes) {

            var permissionNeeded = attributes.permissionNeeded;

            if (permissionNeeded) {
                if (SecurityService.checkAccess($route.current.name) !== permissionNeeded) {
                    element.remove();
                }
            }
        }
    };
});

Директива работает нормально, однако я не могу ее проверить. Манипуляции с DOM (element.remove()), кажется, запускаются после моего ожидаемого утверждения:

 it('should not do anything cos permissions are correct', function () {
        $route.current = {
            name: 'import'
        }
        var element = compileTemplate('<span permission-needed="W">Some content goes here</span>');
        $rootScope.$digest();
        expect(element.html()).toBe(''); // FAIL!!! it's still equals to 'Some Content goes here'
    });

Я видел несколько ответов на SO об использовании функции $timeout для задержки ожидания утверждения, но что бы я ни пробовал, утверждение терпит неудачу (element.html() по-прежнему равно «Некоторый контент идет сюда»)

Однако забавно (правильно?) то, что если я просто изменю dom вместо того, чтобы удалить его в своей директиве, мой тест будет в порядке:

angular.module('app').directive('permissionNeeded', function ($location, $route, SecurityService) {
    return {
        restrict: 'A',
        link: function (scope, element, attributes) {

            var permissionNeeded = attributes.permissionNeeded;

            if (permissionNeeded) {
                if (SecurityService.checkAccess($route.current.name) !== permissionNeeded) {
                    element.html('');
                }
            }
        }
    };
});

используя указанную выше директиву, тест проходит.

Я прав, когда предполагаю, что рендеринг dom еще не закончен, когда я делаю свое утверждение? Если да, то что я могу сделать, чтобы отложить свое утверждение после рендеринга DOM?

Спасибо.

Матье.


person Mat    schedule 09.01.2014    source источник
comment
В вашей первой директиве вы сделали element.remove(), что означает, что элемент будет отсоединен от DOM или, по крайней мере, должен, я думаю.   -  person dcodesmith    schedule 10.01.2014
comment
Я думаю, что dcodesmith прав, элемент все еще является элементом, он просто удален из dom, вы хотите проверить, что он был удален из parentNode.   -  person jeffmayeur    schedule 10.01.2014
comment
Спасибо вам обоим, вы были правы (см. ответ @LostInComputer ниже)   -  person Mat    schedule 10.01.2014


Ответы (1)


Когда вы выполняете element.remove(), он только удаляет элемент из его родителя, удаляет связанные события и т. д..

Самое короткое решение — заключить директиву в родительский элемент:

var element = compileTemplate('<div><span permission-needed="W">Some content goes here</span></div>');

потом

expect(element.html()).toBe('')

пройдет, так как element больше не содержит span

person LostInComputer    schedule 10.01.2014
comment
не могли бы вы добавить планк - person Evan Lévesque; 15.07.2014