7

If I have directive like this

JS:

app.controller('MyController', function($scope) {
  this.someMethod = function() {
  };
});

app.directive('myDirective', function() {
  return {
    scope: true
    link: function(scope, elem, attrs, controller) {
      controller.someMethod();
    }
    controller: 'MyController',
  }
});

I want to create a Jasmine spy to ensure that the link function called controller.someMethod, but this will not work:

Spec:

var elem = angular.element('<div my-directive></div>');
var scope = $rootScope.new();
$compile(elem)(scope);

var ctrl = elem.controller('myDirective');
spyOn(ctrl, 'someFunc').andCallThrough();

The spy is created too late, because the controller was instantiated and the link function called in the $compile statement.

What other ways are there for spying on something that happens in the link function? Is it possible to maybe instantiate the controller before hand and pass it into $compile?

hgcrpd
  • 1,820
  • 3
  • 19
  • 32
  • http://stackoverflow.com/questions/13406491/how-to-test-behavior-in-the-link-function-of-a-directive suggests testing the resulting state, but the state that I am trying to test is not a DOM state. The controller saves the result of the method call and puts it into an array to keep track of the reference, but the reference is not identifiable, so I can only count the length of the array, which seems less than ideal. – hgcrpd Sep 12 '13 at 07:37

1 Answers1

7

From the AngularJS Developer Guide's page on Directives:

Best Practice: use controller when you want to expose an API to other directives. Otherwise use link.

I would suggest creating a service for whatever someMethod() does. Then you can mock and spy on that service. Otherwise you may have to look for some other sign that what you wanted to happen has actually happened.

Austin Thompson
  • 2,251
  • 1
  • 17
  • 23
  • I think this is probably correct. I've learned since asking this question that the structure of your program between controllers, directives, and services is really important for testability. – hgcrpd Mar 14 '14 at 19:35