diff --git a/Gruntfile.js b/Gruntfile.js new file mode 100644 index 0000000..04c8b4d --- /dev/null +++ b/Gruntfile.js @@ -0,0 +1,67 @@ +'use strict'; + +module.exports = function (grunt) { + // configure tasks + grunt.initConfig({ + mocha_parallel: { + options: { + args: function(suiteName) { + return []; + }, + env: function(suiteName) { + process.env.platformName = grunt.option('platformName'); + process.env.platformVersion = grunt.option('platformVersion'); + process.env.deviceName = grunt.option('deviceName'); + process.env.app = grunt.option('app'); + return process.env; + }, + report: function(suite, code, stdout, stderr) { + if (stdout.length) { + process.stdout.write(stdout); + } + if (stderr.length) { + process.stderr.write(stderr); + } + }, + done: function(success, results) { + }, + mocha: './node_modules/.bin/mocha' + } + }, + + parallel: { + assets: { + options: { + grunt: true + }, + tasks: ['run_iPhone_6_Simulator', 'run_iPhone_6_Real_Device'] + } + } + }); + + // load tasks + grunt.loadNpmTasks('grunt-mocha-parallel'); + grunt.loadNpmTasks('grunt-parallel'); + + grunt.registerTask('iPhone_6_Simulator', function(n) { + grunt.option('platformName', 'iOS'); + grunt.option('platformVersion', '8.4'); + grunt.option('deviceName', "iPhone 6"); + grunt.option('app', 'https://s3.amazonaws.com/appium/TestApp8.4.app.zip'); + }); + + grunt.registerTask('iPhone_6_Real_Device', function(n) { + grunt.option('platformName', 'iOS'); + grunt.option('platformVersion', '8.4'); + grunt.option('deviceName', "iPhone 6 Device"); + grunt.option('app', 'sauce-storage:TestApp-iphoneos.app.zip'); + }); + + // register tasks + grunt.registerTask('default', ['parallel']); + + grunt.registerTask('run_iPhone_6_Simulator', ['iPhone_6_Simulator', 'mocha_parallel']); + grunt.registerTask('run_iPhone_6_Real_Device', ['iPhone_6_Real_Device', 'mocha_parallel']); + +}; + diff --git a/README.md b/README.md new file mode 100644 index 0000000..fd243c4 --- /dev/null +++ b/README.md @@ -0,0 +1,29 @@ +# Description +Uses the following technologies / packages +- mocha (https://mochajs.org/) +- grunt-mocha-parallel (https://www.npmjs.com/package/grunt-mocha-parallel) for parallel execution of test suites +- grunt-parallel (https://github.com/iammerrick/grunt-parallel) for parallel execution against multilevel browser / OS configurations. +- wd.js for Appium JS binding + +# Usage + +## Set Sauce Variables: +``` +$ export SAUCE_USERNAME=sauce_username +$ export SAUCE_ACCESS_KEY=sauce_access_key +``` + +## Install Grunt +``` +$ npm install -g grunt # use sudo if necessary +``` + +## Download Node Modules: +``` +$ npm install +``` + +## Run the tests: +``` +$ grunt +``` diff --git a/package.json b/package.json new file mode 100644 index 0000000..5a834e1 --- /dev/null +++ b/package.json @@ -0,0 +1,17 @@ +{ + "name": "mocha-wd-parallel", + "version": "0.0.0", + "description": "Parallel tests with Mocha and WD.js =============", + "main": "", + "devDependencies": { + "wd": "*", + "chai-as-promised": "~4.1.0", + "grunt": "0.4.5", + "grunt-mocha-parallel": "^0.1.7", + "grunt-parallel": "^0.4.1", + "q": "~0.9.7", + "lodash": "~2.4.1", + "chai": "~1.8.1", + "mocha": "1.18.2" + } +} diff --git a/test/example-spec.js b/test/example-spec.js new file mode 100644 index 0000000..e902c30 --- /dev/null +++ b/test/example-spec.js @@ -0,0 +1,17 @@ +var makeSuite = require('./helpers').makeSuite; + +makeSuite('Test Suite 2', function() { + + it('should compute different sum', function() { + driver + .elementByAccessibilityId('TextField1') + .sendKeys(13) + .elementByClassName('UIATextField') + .sendKeys(8) + .elementByAccessibilityId('ComputeSumButton') + .click() + .elementByClassName('UIAStaticText') + .should.eventually.equal(21); + }); + +}); diff --git a/test/example2-spec.js b/test/example2-spec.js new file mode 100644 index 0000000..8b16eb7 --- /dev/null +++ b/test/example2-spec.js @@ -0,0 +1,17 @@ +var makeSuite = require('./helpers').makeSuite; + +makeSuite('Test Suite 1', function() { + + it('should compute a sum', function() { + driver + .elementByAccessibilityId('TextField1') + .sendKeys(12) + .elementByClassName('UIATextField') + .sendKeys(8) + .elementByAccessibilityId('ComputeSumButton') + .click() + .elementByClassName('UIAStaticText') + .should.eventually.equal(20); + }); + +}); diff --git a/test/helpers.js b/test/helpers.js new file mode 100644 index 0000000..ce88368 --- /dev/null +++ b/test/helpers.js @@ -0,0 +1,54 @@ +var wd = require('wd'), + _ = require("lodash"), + chai = require("chai"), + chaiAsPromised = require("chai-as-promised"); + +chai.use(chaiAsPromised); +chai.should(); +chaiAsPromised.transferPromiseness = wd.transferPromiseness; + +wd.configureHttp({ + timeout: 240000, + retryDelay: 15000, + retries: 5 +}); + +function beforeEachExample(done) { + var username = process.env.SAUCE_USERNAME; + var accessKey = process.env.SAUCE_ACCESS_KEY; + driver = wd.promiseChainRemote("ondemand.saucelabs.com", 80, username, accessKey); + + driver + .init({ + name: this.currentTest.title, + browserName: '', + appiumVersion: '1.4.13', + deviceName: process.env.deviceName, + platformVersion: process.env.platformVersion, + platformName: process.env.platformName, + app: process.env.app + }) + .nodeify(done); +}; + +function afterEachExample(done) { + // allPassed = allPassed && (this.currentTest.state === 'passed'); + driver + .quit() + .sauceJobStatus(true) + .nodeify(done); +}; + +function makeSuite(desc, cb) { + describe(desc, function() { + var driver; + + this.timeout(240000); + + beforeEach(beforeEachExample); + cb(); + afterEach(afterEachExample); + }); +}; + +exports.makeSuite = makeSuite;