Made calculator less awful
Diff
wdio.conf.js | 359 ++++++++++++++++++++++++++++++++++++++------------------------------------------
app/calculator.js | 92 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++------------------
app/calculator.test.js | 86 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-------
3 files changed, 192 insertions(+), 345 deletions(-)
@@ -1,295 +1,84 @@
export const config = {
runner: 'local',
specs: [
'./app/**/*.test.js'
],
exclude: [
],
maxInstances: 10,
capabilities: [{
browserName: 'chrome'
}],
runner: 'local',
logLevel: 'debug',
bail: 0,
waitforTimeout: 10000,
connectionRetryTimeout: 120000,
connectionRetryCount: 3,
framework: 'mocha',
reporters: ['spec'],
specs: [
'./app/**/*.test.js'
],
mochaOpts: {
ui: 'bdd',
timeout: 60000
},
maxInstances: 10,
/**
* Gets executed once before all workers get launched.
* @param {object} config wdio configuration object
* @param {Array.<Object>} capabilities list of capabilities details
*/
/**
* Gets executed before a worker process is spawned and can be used to initialize specific service
* for that worker as well as modify runtime environments in an async fashion.
* @param {string} cid capability id (e.g 0-0)
* @param {object} caps object containing capabilities for session that will be spawn in the worker
* @param {object} specs specs to be run in the worker process
* @param {object} args object that will be merged with the main configuration once worker is initialized
* @param {object} execArgv list of string arguments passed to the worker process
*/
/**
* Gets executed just after a worker process has exited.
* @param {string} cid capability id (e.g 0-0)
* @param {number} exitCode 0 - success, 1 - fail
* @param {object} specs specs to be run in the worker process
* @param {number} retries number of retries used
*/
/**
* Gets executed just before initialising the webdriver session and test framework. It allows you
* to manipulate configurations depending on the capability or spec.
* @param {object} config wdio configuration object
* @param {Array.<Object>} capabilities list of capabilities details
* @param {Array.<String>} specs List of spec file paths that are to be run
* @param {string} cid worker id (e.g. 0-0)
*/
/**
* Gets executed before test execution begins. At this point you can access to all global
* variables like `browser`. It is the perfect place to define custom commands.
* @param {Array.<Object>} capabilities list of capabilities details
* @param {Array.<String>} specs List of spec file paths that are to be run
* @param {object} browser instance of created browser/device session
*/
/**
* Runs before a WebdriverIO command gets executed.
* @param {string} commandName hook command name
* @param {Array} args arguments that command would receive
*/
/**
* Hook that gets executed before the suite starts
* @param {object} suite suite details
*/
/**
* Function to be executed before a test (in Mocha/Jasmine) starts.
*/
/**
* Hook that gets executed _before_ a hook within the suite starts (e.g. runs before calling
* beforeEach in Mocha)
*/
/**
* Hook that gets executed _after_ a hook within the suite starts (e.g. runs after calling
* afterEach in Mocha)
*/
capabilities: [
{
browserName: 'firefox'
},
/**
* Function to be executed after a test (in Mocha/Jasmine only)
* @param {object} test test object
* @param {object} context scope object the test was executed with
* @param {Error} result.error error object in case the test fails, otherwise `undefined`
* @param {*} result.result return object of test function
* @param {number} result.duration duration of test
* @param {boolean} result.passed true if test has passed, otherwise false
* @param {object} result.retries information about spec related retries, e.g. `{ attempts: 0, limit: 0 }`
*/
],
logLevel: 'debug',
bail: 0,
waitforTimeout: 10000,
connectionRetryTimeout: 120000,
connectionRetryCount: 3,
framework: 'mocha',
/**
* Hook that gets executed after the suite has ended
* @param {object} suite suite details
*/
/**
* Runs after a WebdriverIO command gets executed
* @param {string} commandName hook command name
* @param {Array} args arguments that command would receive
* @param {number} result 0 - command success, 1 - command error
* @param {object} error error object if any
*/
/**
* Gets executed after all tests are done. You still have access to all global variables from
* the test.
* @param {number} result 0 - test pass, 1 - test fail
* @param {Array.<Object>} capabilities list of capabilities details
* @param {Array.<String>} specs List of spec file paths that ran
*/
/**
* Gets executed right after terminating the webdriver session.
* @param {object} config wdio configuration object
* @param {Array.<Object>} capabilities list of capabilities details
* @param {Array.<String>} specs List of spec file paths that ran
*/
/**
* Gets executed after all workers got shut down and the process is about to exit. An error
* thrown in the onComplete hook will result in the test run failing.
* @param {object} exitCode 0 - success, 1 - fail
* @param {object} config wdio configuration object
* @param {Array.<Object>} capabilities list of capabilities details
* @param {<Object>} results object containing test results
*/
/**
* Gets executed when a refresh happens.
* @param {string} oldSessionId session ID of the old session
* @param {string} newSessionId session ID of the new session
*/
/**
* Hook that gets executed before a WebdriverIO assertion happens.
* @param {object} params information about the assertion to be executed
*/
/**
* Hook that gets executed after a WebdriverIO assertion happened.
* @param {object} params information about the assertion that was executed, including its results
*/
reporters: ['spec'],
mochaOpts: {
ui: 'bdd',
timeout: 60000
}
}
@@ -1,7 +1,8 @@
let operand;
let operation;
let displayString = '0';
let operationComplete = false;
@@ -10,66 +11,81 @@
}
function addDigit(digit) {
if (displayString === '0') {
if (displayString === '0' || operationComplete) {
displayString = digit;
} else {
displayString += digit;
}
operationComplete = false;
updateDisplay();
}
function doAddition() {
operand = parseInt(displayString);
displayString = '0';
operation = '+';
doOperation();
operand = parseInt(displayString);
displayString = '0';
operation = '+';
}
function doSubtraction() {
operand = parseInt(displayString);
displayString = '0';
operation = '-';
doOperation();
operand = parseInt(displayString);
displayString = '0';
operation = '-';
}
function doMultiplication() {
operand = parseInt(displayString);
displayString = '0';
operation = '*';
doOperation();
operand = parseInt(displayString);
displayString = '0';
operation = '*';
}
function doDivision() {
operand = parseInt(displayString);
displayString = '0';
operation = '/';
doOperation();
operand = parseInt(displayString);
displayString = '0';
operation = '/';
}
function doClear() {
operand = undefined;
operation = undefined;
displayString = '0';
updateDisplay();
operand = undefined;
operation = undefined;
displayString = '0';
updateDisplay();
}
function doOperation() {
if (operand === undefined || operation === undefined) {
return;
}
let secondOperand = parseInt(displayString);
if (operation === '+') {
displayString = operand + secondOperand;
} else if (operation === '-') {
displayString = operand - secondOperand;
} else if (operation === '*') {
displayString = operand * secondOperand;
} else if (operation === '/') {
displayString = operand / secondOperand;
}
operationComplete = true;
}
function doEquals() {
if (operand === undefined || operation === undefined) {
return;
}
let secondOperand = parseInt(displayString);
if (operation === '+') {
displayString = operand + secondOperand;
} else if (operation === '-') {
displayString = operand - secondOperand;
} else if (operation === '*') {
displayString = operand * secondOperand;
} else if (operation === '/') {
displayString = operand / secondOperand;
}
operand = undefined;
operation = undefined;
updateDisplay();
displayString = '0';
if (operand === undefined || operation === undefined) {
return;
}
doOperation();
operand = undefined;
operation = undefined;
updateDisplay();
}
function keyPress(event) {
@@ -85,7 +101,7 @@
doDivision();
} else if (event.key === 'Enter') {
doEquals();
} else if (event.key === 'c') {
} else if (event.key === 'c' || event.key === 'Escape') {
doClear();
}
}
@@ -1,28 +1,29 @@
import { $, expect } from '@wdio/globals'
export class CalcPage {
constructor() {
this.title = 'Calculator';
}
open() {
open() {
return browser.url('http://localhost:8000')
}
get doc() { return browser }
get display() { return $('#display') }
get button_one() { return $('#digit_1') }
get button_two() { return $('#digit_2') }
get button_three() { return $('#digit_3') }
get button_four() { return $('#digit_4') }
get button_five() { return $('#digit_5') }
get button_six() { return $('#digit_6') }
get button_seven() { return $('#digit_7') }
get button_eight() { return $('#digit_8') }
get button_nine() { return $('#digit_9') }
get button_zero() { return $('#digit_0') }
get button_1() { return $('#digit_1') }
get button_2() { return $('#digit_2') }
get button_3() { return $('#digit_3') }
get button_4() { return $('#digit_4') }
get button_5() { return $('#digit_5') }
get button_6() { return $('#digit_6') }
get button_7() { return $('#digit_7') }
get button_8() { return $('#digit_8') }
get button_9() { return $('#digit_9') }
get button_0() { return $('#digit_0') }
get operation_add() { return $('#operator_add') }
get operation_multiply() { return $('#operator_multiply') }
@@ -30,6 +31,7 @@
get operation_divide() { return $('#operator_divide') }
get calculate() { return $('#calculate') }
get clear() { return $('#clear') }
}
const calcPage = new CalcPage();
@@ -44,31 +46,31 @@
it('Should be able to add 1 + 2', async () => {
await calcPage.open();
await calcPage.button_one.click();
await calcPage.button_1.click();
await calcPage.operation_add.click();
await calcPage.button_two.click();
await calcPage.button_2.click();
await calcPage.calculate.click();
await expect(calcPage.display).toHaveValue('3');
});
it('Should be able to multiply 5 * 15', async () => {
await calcPage.open();
await calcPage.button_five.click();
await calcPage.button_5.click();
await calcPage.operation_multiply.click();
await calcPage.button_one.click();
await calcPage.button_five.click();
await calcPage.button_1.click();
await calcPage.button_5.click();
await calcPage.calculate.click();
await expect(calcPage.display).toHaveValue('75');
});
it('Should be able to divide 300 by 25', async () => {
await calcPage.open();
await calcPage.button_three.click();
await calcPage.button_zero.click();
await calcPage.button_zero.click();
await calcPage.button_3.click();
await calcPage.button_0.click();
await calcPage.button_0.click();
await calcPage.operation_divide.click();
await calcPage.button_two.click();
await calcPage.button_five.click();
await calcPage.button_2.click();
await calcPage.button_5.click();
await calcPage.calculate.click();
await expect(calcPage.display).toHaveValue('12');
});
@@ -83,5 +85,45 @@
await calcPage.doc.keys('Enter');
await expect(calcPage.display).toHaveValue('500');
});
it('Should be able to subtract 10 - 5', async () => {
await calcPage.open();
await calcPage.button_1.click();
await calcPage.button_0.click();
await calcPage.operation_subtract.click();
await calcPage.button_5.click();
await calcPage.calculate.click();
await expect(calcPage.display).toHaveValue('5');
});
it(`Should detect each digit being pressed`, async () => {
for (var x = 0; x < 9; x++) {
await calcPage.open();
await calcPage[`button_${x}`].click();
await expect(calcPage.display).toHaveValue(`${x}`);
}
});
it ('Should support three operations in a row', async () => {
await calcPage.open();
await calcPage.button_1.click();
await calcPage.operation_add.click();
await calcPage.button_2.click();
await calcPage.operation_multiply.click();
await calcPage.button_3.click();
await calcPage.calculate.click();
await expect(calcPage.display).toHaveValue('9');
});
it('The clear button should work', async () => {
await calcPage.open();
await calcPage.button_1.click();
await calcPage.operation_add.click();
await calcPage.button_2.click();
await calcPage.calculate.click();
await expect(calcPage.display).toHaveValue('3');
await calcPage.clear.click();
await expect(calcPage.display).toHaveValue('0');
});
});