Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can I unit test isolated scope in directive

I am trying to unit test a simple directive but the variable in the scope is always undefined.

Directive Src Code:

.directive('ratingButton', ['$rootScope',


function($rootScope) {
      return {
          restrict: "E",
          replace: true,
          template: '<button type="button" class="btn btn-circle" ng-class="getRatingClass()"></button>',
          scope: {
              buttonRating: "="
          },
          link: function(scope, elem, attr) {
              scope.getRatingClass = function() {
                  if (!scope.buttonRating)
                      return '';
                  else if (scope.buttonRating.toUpperCase() === 'GREEN')
                      return 'btn-success';
                  else if (scope.buttonRating.toUpperCase() === 'YELLOW')
                      return 'btn-warning warning-text';
                  else if (scope.buttonRating.toUpperCase() === 'RED')
                      return 'btn-danger';
                  else if (scope.buttonRating.toUpperCase() === 'BLUE')
                      return 'btn-info';
              }
          }
      };
  }])

Test:

describe('Form Directive: ratingButton', function() {

    // load the controller's module
    beforeEach(module('dashboardApp'));

    var scope,
        element;

    // Initialize the controller and a mock scope
    beforeEach(inject(function($compile, $rootScope) {
        scope = $rootScope.$new();

        //set our view html.
        element = angular.element('<rating-button button-rating="green"></rating-button>');
        $compile(element)(scope);
        scope.$digest();
    }));

    it('should return appropriate class based on rating', function() {
        //console.log(element.isolateScope());
        expect(element.isolateScope().buttonRating).toBe('green');
        expect(element.isolateScope().getRatingClass()).toBe('btn-success');

    });

});

I used similar code in another directive unit test I had by passing values through element attributes and it worked as expected. For this test buttonRating is always undefined not sure where to go from here(I am fairly new with Jasmine/Karma)

Any help would be great!

like image 399
atsituab Avatar asked Jan 12 '15 01:01

atsituab


1 Answers

Instead of setting string green set it on the scope bound when the directive element is compiled in your startup of the test. Otherwise it will look for the value of scope property with the name green on the bound scope, and which of course is not defined in your case.

i.e scope.buttonRating = 'green';

and

angular.element('<rating-button button-rating="buttonRating"></rating-button>')

Try:

  // Initialize the controller and a mock scope
    beforeEach(inject(function($compile, $rootScope) {
        scope = $rootScope.$new();
        scope.buttonRating = 'green'; //<-- Here
        //set our view html.
        element = angular.element('<rating-button button-rating="buttonRating"></rating-button>');
        $compile(element)(scope);
        scope.$digest();
    }));

    it('should return appropriate class based on rating', function() {
        expect(element.isolateScope().buttonRating).toBe('green');
        expect(element.isolateScope().getRatingClass()).toBe('btn-success');

    });

Plnkr

like image 131
PSL Avatar answered Nov 02 '22 05:11

PSL