【问题标题】:Infinite Digest when Mocking $location模拟 $location 时的无限摘要
【发布时间】:2014-01-21 21:27:29
【问题描述】:

我发现,如果我尝试模拟 Angular 的 $location 服务,然后我需要在测试中强制执行任何类型的摘要,那么我会收到一个无限摘要错误。我的控制器中的代码是什么并不重要。我已经用一个完全空的控制器尝试了这个,它只将 $location 作为参数,如果我在我的测试中做一个摘要,它就失败了。

Here's a fiddle 这是我对小提琴的测试:

describe('fooController', function() {
    var controller, mocklocation, scope;

    beforeEach(function() {
        module("myModule");

        inject(function($rootScope, $controller, $location) {
            scope = $rootScope.$new();

            mocklocation = sinon.stub($location);
            controller = $controller("FooController", { $scope: scope, $location: location });
        });
    });

    describe('when calling $digest in a test', function () {
        beforeEach(function () {
            //do some stuff here and then resolve a promise

            //call digest to cause the resolved promise to get evaluated
            scope.$root.$digest();
        });
        it('should not get infinite digests', function () {

        });
    });
});

请注意,我在该测试中所做的只是一个 scope.$root.$digest。在我的真实代码中,我在那个摘要之前解决了一个承诺,所以这就是我需要做这个摘要的原因。

【问题讨论】:

  • 能否分享需要摘要的代码。什么样的承诺需要根摘要?
  • 如果需要,为了清晰起见,我可以在代码中添加一些内容,但代码本身不需要摘要。我在我的 jasmine 测试中解决了一个 promise,并且为了让 Angular 处理该 promise.resolve(),我必须在我的测试中调用 digest。
  • 如果promise 是由$http 生成的,则不会使用$httpBackend。这就是为什么最好看看你必须解决什么承诺。

标签: angularjs testing mocking


【解决方案1】:

与其尝试模拟整个 $location 服务,我建议您手动滚动自己的模拟并仅存根您需要测试的内容。例如,如果您使用 mockLocation 断言使用特定路径调用 path 函数,您可以像这样设置您的 mock:

mockLocation = { path: sinon.stub() };

然后你仍然可以这样断言:

expect(mockLocation.path.calledWith(...)).toBeTruthy();

我不确定为什么存根整个对象会导致无限摘要(这些都太棘手了!)但这至少应该让您继续前进。此外,在您的测试中,确保您在注入 mockLocation 对象时发送它(现在您有“$location: location”)。

 controller = $controller("FooController", { $scope: scope, $location: mockLocation });

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-03-21
    • 2011-07-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多