javascript - 单元测试 AngularJS 指令包装 Snap.svg

标签 javascript angularjs unit-testing snap.svg

我正在尝试创建一个 Angular 指令来包装 Snap.svg 功能,但我在对其进行单元测试时遇到了问题。到目前为止,我有一个看起来像这样的指令:

'use strict';

angular.module('rpApp')
  .directive('rpSvgMap', function () {
    return {
      template: '<svg id="" width="" height=""></svg>',
      restrict: 'E',
      replace: true,
      // Don't isolate scope because we want to attach rpMap to parent scope
      link: function postLink(scope, element, attrs) {
        // Set up Snap.svg wrapper
        scope.rpMap = Snap('#' + attrs.id);
      }
    };
  });

我的 Karma/Jasmine 测试看起来像这样:

'use strict';

describe('Directive: rpSvgMap', function () {

  // load the directive's module
  beforeEach(module('rpApp'));

  var element,
    scope;

    beforeEach(inject(function($rootScope,$compile) {
        scope = $rootScope.$new();
        element =
      '<rp-svg-map id="anyOldID" width="800" height="400" src="../../assets/testmap.svg"></rp-svg-map>';

        element = $compile(element)(scope);
        scope.$digest();
  }));

  describe('on initialization', function() {
    it('should create an SVG element with the provided dimensions and id', function() {
      expect(element.attr('id')).toBe('anyOldID');
      expect(element.attr('height')).toBe('400');
      expect(element.attr('width')).toBe('800');
    });
    it('should provide a working Snap.svg drawing surface', function() {
      var testCircle = scope.rpMap.circle(100,150,200);
      expect(testCircle.attr(cx)).toBe(100);
    });

});

第一个测试通过,第二个测试失败,因为 scope.rpMap 总是返回“null”。

在浏览器中,这工作得很好——如果我将 $scope 附加到我的 Controller 中的窗口,rpMap 会被 Snap.svg 正确包装并且 rpMap.circle() 会正确绘制一个圆。

据我所知,测试环境正在正确加载 snap.svg 作为依赖项,并且我正在从指令中正确读取范围。例如,如果我添加:

scope.hasSnap = angular.isFunction(Snap);

到指令的链接函数,然后这个测试通过:

it('should tell us when Snap.svg is available', function() {
      expect(scope.hasSnap).toBe(true);
    });

Snap() 不是异步的,将 beforeAll/it 更改为异步模式也无济于事。

知道我在这里做错了什么吗?

最佳答案

我找到的这个 jsfiddle(抱歉,不记得来源)包含解决方案 http://jsfiddle.net/hRy4A/2/

具体来说,我们可以像这样将元素直接传递给 Snap:

scope.rpMap = Snap(element[0]);

当以这种方式创建 rpMap 时,以下测试通过:

it('should provide a working Snap.svg drawing surface', function() {
        var testCircle = scope.rpMap.circle(100,150,200);
        expect(testCircle.attr('cx')).toBe('100');
        expect(testCircle.attr('cy')).toBe('150');
        expect(testCircle.attr('r')).toBe('200');
    });

我想这种方法的一个潜在问题是我不一定需要或不想在 $scope 中公开所有 Snap.svg 方法——我想理想情况下,图形内容将全部独立在指令中.

注意我原来的测试也有一个小错别字,应该是

expect(testCircle.attr('cx')).toBe('100');

关于javascript - 单元测试 AngularJS 指令包装 Snap.svg,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31105460/

相关文章:

javascript - 仅使用特定参数返回特定值

c# - Moq.Dapper QueryAsync 不适用于模拟事务对象

javascript - Gatsbyjs - 如何使用 Material UI Lib 提取 GraphQL 数据

javascript - 任何人都可以用一种易于理解的方式从字面上翻译这个 JavaScript 函数吗?

javascript - Node.js 使用 Promise 递归下载分块数组

javascript - 嵌套在 Popover 中的 ng-repeat 不起作用

javascript - 为什么我的 ng-class 即使在 false 时也会显示

angularjs - 如何向 Angular 的 Controller /$scope 提供初始数据?

javascript - 无法覆盖键盘 ALT 修饰符

ios - CloudKit 的单元测试