繁体   English   中英

如何:模拟模块依赖项

[英]How to: mock module dependencies

撕下我的头发。

我有以下要测试的模块/控制器

angular
    .module('monitor.tableLord.controller', ['monitor.wunderTable'])
    .controller('TableLordController', TableLordController);

    TableLordController.$inject = ['$scope', 'historyState'];
    function TableLordController($scope, historyState) {
        ....some code....
    }

monitor.wunderTable模块包含应在控制器之前加载的指令,但是我要测试的控制器实际上并不依赖于monitor.wunderTable。 monitor.wunderTable确实还有很多其他依赖项。

我的测试文件:

describe('TableLordController', function() {
    var $scope, historyState;

    beforeEach(function() {
        angular.module('monitor.wunderTable', []);
        module('monitor.tableLord.controller');
    });

    beforeEach(angular.mock.inject(function($rootScope, $controller) {
            $scope = $rootScope.$new();
            $controller('TableLordController', {$scope: $scope, historyState: {}});
    }));

    it('loads', function() {
        $scope.$digest();
    });
});

由于某种原因(我认为这不可能),我的模拟版本Monitor.wunderTable干扰了我对该模块的测试。 现在,此模块中定义的控制器的所有测试都会失败,并显示:“参数'WunderTableController'不是函数,未定义”。

我认为这是相关的,这是我对monitor.wunderTable的定义:

angular
    .module('monitor.wunderTable', [
        'ui.grid',
        'ui.grid.infiniteScroll',
        'ui.grid.autoResize',
        'monitor.wunderTable.service'
     ])
    .controller('WunderTableController', WunderTableController)
    .directive('wunderTable', wunderTable);

function wunderTable(){...}
WunderTableController.$inject = [];
function WunderTableController(...){...}

编辑:暗示我删除模块依赖项的帖子(因为不是严格需要的)将不被接受为正确答案(并且可能被低估)。

您的困惑来自对模块在Angular中的工作方式的误解。 模块存储在angular 一旦覆盖它们,它们将被当前测试运行覆盖,而不是被当前规范覆盖。 ngMock不支持模块模拟(这需要在Angular核心中进行一些实质性更改),而beforeEach将无济于事。

除非您要在单独的运行中运行测试套件,否则解决方案是在对模块进行模拟之前对其进行备份。 在某些情况下, angular.extendangular.copy无法正确处理复杂的对象。 Object.assignjQuery.extendnode-extend可能是更好的选择。 extend的情况下,如有必要,也可以使用深层复制。

所以在一个测试套件中

var moduleBackup = angular.module('monitor.wunderTable');
angular.module('monitor.wunderTable', []);

describe('TableLordController', function() {
    ...

而在另一个

Object.assign(angular.module('monitor.wunderTable'), moduleBackup);

describe('WunderTableController', function() {
    ...

TDD的优点在于,它可以清楚地指出应用程序设计中的缺陷,并教会开发人员以立即无情的方式编写易于测试的代码。 模块依赖性意味着模块内部的组件依赖于另一个组件。 如果没有,或者耦合太紧密,则可以认为这是潜在的缺陷,是重构的主题。

该解决方案容易被破解并且容易崩溃的事实使其不适合测试。

TL; DR:是的,您必须删除模块依赖性。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM