【问题标题】:Jasmine test input with pattern茉莉花测试输入与模式
【发布时间】:2016-10-13 14:55:29
【问题描述】:

我有一个包含以下输入的表单:

<input type="email" name="email" ng-model="register.form.email" ng-pattern="emailRegex">

如果用户输入无效的电子邮件,我想测试该表单是否无效:

it('...', function() {
    form.email.$setViewValue('invalid');
    expect(form.email.$valid).toBeFalsy(); // OK
    form.email.$setViewValue('invalid@');    
    expect(form.email.$valid).toBeFalsy(); // OK
    form.email.$setViewValue('invalid@host');     
    expect(form.email.$valid).toBeFalsy(); // Not OK    
});

最后一个期望失败,因为输入是有效的,尽管电子邮件正则表达式需要一个域。感觉好像在我的测试中没有使用该模式,因为当我将类型更改为文本时,它已经在第一个期望中失败了。如何确保在测试中采用该模式?

为了完整起见,这是正则表达式(不是我写的):

^[_A-Za-z0-9-]+(\.[_A-Za-z0-9-]+)*@[_A-Za-z0-9]+[_A-Za-z0-9-]*[_A-Za-z0-9]+(\.[A-Za-z0-9]+)*(\.[A-Za-z]{2,})$

将类型更改为text 无效。

我正在使用 jasmine 2.4.1 和 angular 1.4.2。我正在使用 ngHtml2JsPreprocessor 解释 here 在我的测试中初始化表单。

编辑:

这是如何初始化表单的:

beforeEach(inject(function($rootScope, $templateCache, $compile) {
   var $scope = $rootScope.$new();
    vm = $controller('RegisterController', {$scope: $scope});
    var templateHtml = $templateCache.get("register.html");
    var template = angular.element("<div>" + templateHtml + "</div>");
    $compile(template)($scope);
    var form = $scope.registerForm;
    $scope.$apply();
    scope = $scope;
}));

【问题讨论】:

  • 该测试能证明什么? ng-pattern 有效吗?是的 - 它有效,可能响应开发 AngularJS 的团队会在您之前发现该错误。你想测试正则表达式吗?提取它并在单元测试中测试它

标签: angularjs forms unit-testing jasmine


【解决方案1】:

AngularJS 仍然以这种方式工作,它是如何开发的

angular.module('app', [])

describe('Registration form', () => {
  'use strict'

  beforeEach(module('app'))

  let form
  let scope

  beforeEach(inject(($rootScope, $compile) => {
    scope = $rootScope.$new()
    var formElem = ['<form name="registrationForm">',
      '<input type="text" name="number" ng-model="input" ng-pattern="/^[_A-Za-z0-9-]+(\.[_A-Za-z0-9-]+)*@[_A-Za-z0-9]+[_A-Za-z0-9-]*[_A-Za-z0-9]+(\.[A-Za-z0-9]+)*(\.[A-Za-z]{2,})$/">',
      '</form>'
    ].join('')
    $compile(formElem)(scope)
    form = scope.registrationForm
  }))

  it('has no `$valid` state', () => {
    expect(form.$valid).toBeTruthy()
    form.number.$setViewValue('invalid email address')
    expect(form.number.$valid).toBeFalsy()
  })

  it('has `$valid` state', () => {
    expect(form.$valid).toBeTruthy()
    form.number.$setViewValue('some@valid.address')
    expect(form.number.$valid).toBeTruthy()
  })
})
<script src="https://safjanowski.github.io/jasmine-jsfiddle-pack/pack/jasmine-2.0.3-concated.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular-mocks.js"></script>
<link href="https://safjanowski.github.io/jasmine-jsfiddle-pack/pack/jasmine.css" rel="stylesheet" />

【讨论】:

  • 正如您所展示的,它确实按我的预期工作,所以我将从您的示例开始构建我的测试用例。关于您的其他评论:遗憾的是,即使我知道它没有那么有用,我也必须编写这个特定的测试。非常感谢!
  • 一些可用于验证电子邮件地址的常用正则表达式 - emailregex.com
【解决方案2】:

我认为你应该在使用form.email.$setViewValuescope 之后调用scope.$digest();,将范围传递给你的$compile。这就是我在每次测试中使用的。

您还可以在这里查看更多信息:https://stackoverflow.com/a/22772504/4583079

【讨论】:

  • 我试过了,不幸的是它不起作用。我可以看到,在最后一个期望之前,modelValue 已经是invalid@host,这意味着它已经通过了解析器和验证器(如果我没记错的话)。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-09-27
相关资源
最近更新 更多