Angular指令的Jasmine单元测试

时间:2014-11-20 15:48:27

标签: angularjs unit-testing angularjs-directive jasmine

我有以下角度指令,当我将鼠标悬停在跨度上时会添加工具提示。

angular.module('mainMod')
    .directive('toolTip', [function() {
        return {
            restrict: 'A',
            scope: {
                theTooltip: '@toolTip'
            },
            link: function(scope, element, attrs){
                element.tooltip({ 
                        delay: 0, 
                        showURL: false, 
                        bodyHandler: function() {
                            return jQuery('<div class="hover">').text(scope.theTooltip);
                        } 
                });
            }
        }
    }])
    ;


<span ng-show="data.tooltip" class="icon" tool-tip="{{data.tooltip}}"></span>

我正在为这个指令编写一个单元测试,atm我不能使用jasmine-jquery

我对编写单元测试相当新,有人可以帮助我吗?

给我一​​些指示或指向一些有用的资源?

非常感谢任何建议或建议。

我的atm并不多......

describe('Unit testing tooltip', function() {
    var $compile;
    var $rootScope;

    // Load the myApp module, which contains the directive
    beforeEach(module('mainMod'));

    // Store references to $rootScope and $compile
    // so they are available to all tests in this describe block
    beforeEach(inject(function(_$compile_, _$rootScope_){
      // The injector unwraps the underscores (_) from around the parameter names when matching
      $compile = _$compile_;
      $rootScope = _$rootScope_;
    }));


    it(' ', function() {
        // Compile a piece of HTML containing the directive
        FAILS HERE --> var element = $compile("<span class='icon' tool-tip='{{data.tooltip}}'></span>")($rootScope); 

        $rootScope.$digest();

    });
});

失败了

的消息
TypeError: undefined is not a function

我认为这是由我在上面指定的行末尾的($ rootScope)引起的。

2 个答案:

答案 0 :(得分:2)

在编译之前,必须首先使用angular.element包装DOM内容。我不确定您使用的工具提示模块是什么,但我使用的是jQuery UI工具提示。

    //create a new scope with $rootScope if you want
    $scope  = $rootScope.$new();

    var element = angular.element("<span class='icon' tool-tip='This is the tooltip data'></span>");

    //use the current scope has just been created above for the directive
    $compile(element)($scope);

还有一件事,因为您在指令中使用隔离范围,要从指令获取当前范围,您需要调用

   element.isolateScope()

基于此参考:How to Unit Test Isolated Scope Directive in AngularJS

对于工作小提琴,您可以在此处找到它:http://jsfiddle.net/themyth92/4w52wsms/1/

答案 1 :(得分:-1)

任何单元测试基本相同 - 模拟环境,构建单元,检查单元是否以预期方式与环境交互。在这种情况下,您可能想要模拟工具提示创建者

spyOn(jQuery.fn, 'tooltip');

然后使用该指令(您已经在做)编译一些模板,然后模拟编译元素上的悬停事件,然后检查工具提示创建者是否以预期方式调用

expect(jQuery.fn.tooltip).toHaveBeenCalledWith(jasmine.objectContaining({
    // ... (expected properties)
}));

如何模拟事件取决于element.tooltip应该如何工作。如果它真的按照您在问题代码中使用它的方式运行,那么您根本不需要模拟任何内容,只需在模板编译后立即检查预期的交互。