angularJS 中的单元测试控制器

Unit testing controllers in angularJS

我很难理解 angularJs 中的单元测试。我刚刚开始进行单元测试,语法对我来说似乎很奇怪。下面是测试 controller :

的代码
describe('PhoneCat controllers', function() {

  describe('PhoneListCtrl', function(){

    beforeEach(module('phonecatApp'));

    it('should create "phones" model with 3 phones',
    inject(function($controller) {
      var scope = {},
      ctrl = $controller('PhoneListCtrl', {$scope:scope});

      expect(scope.phones.length).toBe(3);
    }));

  });
});

我从这个语法中可以理解的是,在每个 it 块 phonecatApp 被初始化之前, $controller 服务被用来获取PhoneListCtrl 控制器的实例。

但是我无法理解这里的范围。有人可以详细说明在这条线上获取控制器范围的背后是什么吗?

ctrl = $controller('PhoneListCtrl', {$scope:scope});

通常,在运行时,angular 创建一个作用域并将其注入控制器函数以实例化它。 在您的单元测试中,您反而想自己创建范围并将其传递给控制器​​函数,以便能够在构建后查看它是否确实有 3 个手机(例如)。

您可能还想将模拟服务而不是真实服务注入到您的控制器中。这就是对象数组在

中所允许的
$controller('PhoneListCtrl', {$scope:scope});

它告诉 angular:创建一个名为 'PhoneListCtrl' 的控制器实例,但不要创建和注入作用域,而是使用我给你的那个。

如果您的控制器依赖于服务 'phoneService',并且您想注入一个模拟电话服务,您可以这样做

var mockPhoneService = ...;
$controller('PhoneListCtrl', { 
    $scope: scope,
    phoneService: mockPhoneService
});

不需要注入范围,您可以直接使用控制器的实例来调用控制器的函数,objects.In您可以像下面这样使用您的示例,这将给出与您的相同的结果集

describe('PhoneCat controllers', function() {

  describe('PhoneListCtrl', function(){

     beforeEach(module('phonecatApp'));

       it('should create "phones" model with 3 phones',
           inject(function($controller) {

      var ctrl = $controller('PhoneListCtrl');

  expect(ctrl.phones.length).toBe(3);
  }));

  });
});

并为您提供信息,每次实例化控制器时,它都绑定到一个从 $rootScope 派生的 $scope 变量(即:rootscope 的子级)。所以你需要传递 $scope 来获取控制器的实例,我在上面的例子中做了同样的事情。