尝试使用 AngularJS 进行一些 BDD,因此我正在尝试使用 Protractor 和 CucumberJS 自动化场景。奇怪的是,试图让步骤定义智能地失败是魔鬼的工作。
Features.feature
Feature: Calculator
As a user
I want to perform arithmetic operations
So that I don't have to think too hard
Scenario: Addition
Given I have opened the calculator application
When I add 2 and 2
Then the result 4 should be displayed
步骤.js
module.exports = function() {
this.Given(/^I have opened the calculator application$/, function (callback) {
//load protractor config baseurl
browser.get('').then(
callback());
});
this.When(/^I add (\d+) and (\d+)$/, function (arg1, arg2, callback) {
//enter numbers to be added
element(by.model('firstNumber')).sendKeys(arg1);
element(by.model('secondNumber')).sendKeys(arg2);
//select mathematical operator from dropdown list
element(by.css('select')).click();
element(by.css('select option[value="0"]')).click();
//hit the calculate button
element(by.buttonText('=')).click();
callback();
});
this.Then(/^the result (\d+) should be displayed$/, function (arg1, callback) {
element(by.binding('result')).getText()
.then(function(result){
result === arg1 ? callback() : callback.fail();
});
});
};
索引.html
<!doctype html>
<html class="no-js">
<head>
<meta charset="utf-8">
<title></title>
</head>
<body ng-app="calculator" ng-controller="MainCtrl">
<input ng-model="firstNumber">
<select ng-model="selectedOperation" ng-options="op as op.value for op in operations"></select>
<input ng-model="secondNumber">
<button ng-click="Calculate()">=</button>
<span ng-bind="result"></span>
<script src="bower_components/angular/angular.js"></script>
<script src="scripts/app.js"></script>
</body>
</html>
应用程序.js
angular
.module('calculator', [])
.controller('MainCtrl', function ($scope) {
$scope.operations = [
{ label: 'Add', value: '+' },
{ label: 'Subtract', value: '-' }
];
$scope.selectedOperation = $scope.operations[0];
$scope.Calculate = function(){
switch($scope.selectedOperation.label) {
case 'Add':
var result = Number($scope.firstNumber) + Number($scope.secondNumber);
break;
case 'Subtract':
var result = Number($scope.firstNumber) - Number($scope.secondNumber);
break;
};
$scope.result = result !== NaN || result === 0 ? result : 'Boo! bad input!';
};
});
量角器输出:
1 个场景(1 个通过) 3 个步骤(3 个通过)
上面的设置工作正常。Protractor 给出了正确的输出,我可以通过在 Then() 步骤中评估不正确的结果来使场景失败。看起来很好。
我看到的第一个问题是当我尝试使 When 步骤失败时。例如,使用上面相同的设置,但尝试定位不存在的元素。
this.When(/^I add (\d+) and (\d+)$/, function (arg1, arg2, callback) {
//enter numbers to be added. Sabotage edition!
element(by.model('AintNoGood')).sendKeys(arg1);
element(by.model('secondNumber')).sendKeys(arg2);
//select mathematical operator from dropdown list
element(by.css('select')).click();
element(by.css('select option[value="0"]')).click();
//hit the calculate button
element(by.buttonText('=')).click();
callback();
});
量角器输出:NoSuchElementError: No element found using locator: by.model("AintNoGood") ... 1 个场景(1 个失败)3 个步骤(1 个失败,2 个通过)
第二步正确失败。我的印象是,当一个步骤失败时,所有后续步骤都会被跳过,但量角器会继续进行第三步,但无论如何都会通过。
更奇怪的是......我清空了 HTML。BDD 测试优先。
索引.html
<!doctype html>
<html class="no-js">
<head>
<meta charset="utf-8">
<title></title>
</head>
<body ng-app="calculator" ng-controller="MainCtrl">
<!--Ghost town here-->
<script src="bower_components/angular/angular.js"></script>
<script src="scripts/app.js"></script>
</body>
</html>
假设我一次一步地经历这个场景,我为第二步编写定义,假设它会失败。
module.exports = function() {
this.Given(/^I have opened the calculator application$/, function (callback) {
//load protractor config baseurl
browser.get('').then(
callback());
});
this.When(/^I add (\d+) and (\d+)$/, function (arg1, arg2, callback) {
//enter numbers to be added
element(by.model('firstNumber')).sendKeys(arg1);
element(by.model('secondNumber')).sendKeys(arg2);
//select mathematical operator from dropdown list
element(by.css('select')).click();
element(by.css('select option[value="0"]')).click();
//hit the calculate button
element(by.buttonText('=')).click();
callback();
});
this.Then(/^the result (\d+) should be displayed$/, function (arg1, callback) {
callback.pending();
});
};
量角器输出:1 个场景(1 个待处理)3 个步骤(1 个待处理,2 个通过)
这样第二步就通过了。显然,它不应该在它应该位于 html 中的任何元素都没有时。
问题:
知道这里发生了什么吗?
如果没有,在我花更多时间试图理解它之前,我想知道是否有人成功地将 Protractor 与 CucumberJS 一起使用?