Permalink
Browse files

seperated rinuts web service from the nodeunit driver. Now this pacak…

…ge consists of only the rinuts service which takes in a driver and exposes a RESTful api to display and activate the driver's tests
  • Loading branch information...
1 parent 8454eb8 commit 18e44e76c3ede89534cb665bcae9afcbef8e6247 @urigolani committed Oct 18, 2011
Showing with 159 additions and 427 deletions.
  1. +20 −25 Readme.md
  2. +34 −0 example/mockRinutsDriver.js
  3. +0 −11 example/testSuite1.js
  4. +14 −4 example/usageExample.js
  5. +0 −215 lib/nodeunitDriver.js
  6. +87 −7 lib/rinuts.js
  7. +0 −71 lib/singleTestReporter.js
  8. +0 −88 lib/webTestService.js
  9. +4 −6 package.json
View
@@ -1,9 +1,9 @@
# rinuts
- Exposes nodeunit based tests through a RESTful api, allowing to remotely query for the urls of supported tests and to activate them, receiving a detailed test run summary.
+ A service which exposes tests through a RESTful api. Allows for remote querying and running tests on the service, by using http requests", as well as retrieving a detailed run information
- built on [node](http://nodejs.org) , [nodeunit](http://github.com/caolan/nodeunit) and [express](http://github.com/visionmedia/express)
+ built on [node](http://nodejs.org) and [express](http://github.com/visionmedia/express)
## Installation
@@ -16,45 +16,40 @@
### Starting the service:
var path = require('path'),
- rinuts = require('rinuts');
-
- rinuts.listen([path.resolve('/tests/testFolder'), path.resolve('../tests/testSuite1.js'), require('../testSuite2')], 9999);
+ rinuts = require('rinuts'),
+ someDriver = require('rinuts-someDriver'),
+ service;
+
+ // what ever api the driver has to load tests
+ someDriver.addTests(*TESTS*);
+
+ service = new rinuts(someDriver);
+ service.listen(3333);
### Service API:
- * listen(modules, port)
- Loads 'modules' and starts listening for requests on 'port'.
- [Argument] port - string specifying the port number to listen on.
- [Argument] modules - any of the following : a nodeunit module | a path to nodeunit file |
- a path to a directory (includes subdirs) | an array containing any of the previous.
+ * *ctor* (driver)
+ Constructor. Loads a driver which implementes 'enumTests' and 'runTest'.
+ [Argument] driver - The driver
### HTTP exposed API:
* GET /tests : JSON response with a list of the tests exposed. Each test includes it's unique name and a POST URL which can be used to execute it. The list structure is as follows:
{
- "*moduleName_testName*": {
+ "*testName*": {
"name": "*testName*",
- "url":"/tests/*moduleName*/*testName*"
+ "url":"/tests/*testName*"
}
...
}
* GET /tests/:testName : Returns an individual entry from the list above. has the form of:
{
"name": "*testName*",
- "url": "/tests/*moduleName*/*testName*"}
+ "url": "/tests/*testName*"}
- * POST /tests/:testName : Executes the individual test and returns the test run summary, including stdout/err capture, in the following structure:
+ * POST /tests/:testName : Executes the individual test and returns the test run summary, in the following structure (can be expanded by the driver):
{
- "name": *testName*,
- "duration": *in milliseconds*,
- "state": *true|false*,
- "assertions": [{
- "method": *ok | fail etc...*
- "success": *true|false*,
- "message": *assertion message*, // included only for failed tests
- "stack": *stack trace*, // included only for failed tests
- },
- ...
- ]
+ "name": *testName*,
+ "state": *true|false*
}
@@ -0,0 +1,34 @@
+var driver = function (tests) {
+ this.init(tests);
+};
+
+module.exports = driver;
+
+driver.prototype = {
+ init: function (tests) {
+ this.tests = tests;
+
+ },
+ enumTests: function (callback) {
+ var tests = [],
+ key;
+
+ console.log(this.tests.length);
+ for (key in this.tests) {
+ if (this.tests.hasOwnProperty(key)) {
+ tests.push(this.tests[key].name);
+ }
+ }
+
+ callback(null, tests);
+ },
+ runTest: function (testName, callback, context) {
+ var test = this.tests[testName],
+ responseFormat = {
+ name: testName,
+ state: test.method()
+ };
+
+ callback(null, responseFormat);
+ }
+};
View
@@ -1,11 +0,0 @@
-// Test File
-
-exports.test1 = function (test){
- test.ok(true, 'Test should pass');
- test.done();
-};
-
-exports.test2 = function (test){
- test.fail(true, 'Test should fail');
- test.done();
-};
View
@@ -1,8 +1,18 @@
var path = require('path'),
- rinuts = require('./../index.js');
-
-//rinuts.listen([path.resolve('testFold'), path.resolve('testSuite1.js')], 9999);
-rinuts.listen(require('./testSuite1'), 9999);
+ rinuts = require('./../index.js'),
+ driver = require('./mockRinutsDriver.js');
+
+var mockdriver = new driver({
+ test1: {
+ name: 'test1',
+ method: function () {
+ return true;
+ }
+ }
+});
+
+var rinutsService = new rinuts(mockdriver);
+rinutsService.listen(9999);
View
@@ -1,215 +0,0 @@
-//jslint igonres
-/*globals module, console, require */
-
-var reporter = require('./singleTestReporter'),
- fs = require('fs'),
-
-//
-// private methods:
-
-//
-// enumarates a group of tests by recursivly flatenning the tree-like structure which nodeunit tests posses through groups,
-// applying a formatter function on each test that determines the test's data structure.
-// test names are prefixed by their containing group followed by a '.'
-// returns an array of tests after applying the formatter on each of them.
- mapTestTree = function (group, formatter, namePrefix) {
- var tests = [],
- key,
- test,
- testName;
-
- function addTest(test) {
- tests.push(test);
- }
-
- for (key in group) {
- if (group.hasOwnProperty(key)) {
- if (typeof group[key] === 'function') {
- testName = namePrefix ? namePrefix + key : key;
- test = formatter(group[key], testName);
- addTest(test);
- } else { // else key is a group of tests
- mapTestTree(group[key], formatter, (namePrefix ? (namePrefix + key + '.') : (key + '.'))).forEach(addTest);
- }
- }
- }
-
- console.log('tests in mapTestTree are : ' + tests);
- return tests;
- },
-
- //
- // Checks if a given path is a directory and applies 'cb' on the boolean result
- isDirectory = function (path, cb) {
- fs.stat(path, function (err, stat) {
- if (err) {
- cb(err);
- return;
- }
-
- if (stat.isDirectory()) {
- cb(null, true);
- } else {
- cb(null, false);
- }
- });
- },
-
- //
- // Loads all tests contained in 'module'.
- // Applies 'callback' on each of the contained tests.
- loadModule = function (module, callback) {
- var tests = [];
-
- tests = mapTestTree(module, function (test, testName) {
- return {
- testName: testName,
- metadata: test
- };
- });
-
- callback(tests);
- },
-
- //
- // Loads all tests contained in the file at 'filePath'.
- // Applies 'callback' on each of the contained tests.
- loadfile = function (filePath, callback) {
- var module = require(filePath);
-
- loadModule(module, callback);
- },
-
- //
- // Loads tests from files and subdirectories contained in the directory at 'dirPath'.
- // Applies 'callback' on each of the contained tests.
- loadDir = function (dirPath, callback) {
- fs.readdir(dirPath, function (err, list) {
- if (err) {
- callback(err);
- return;
- }
-
- list.forEach(function (file) {
- file = dirPath + '/' + file;
- isDirectory(file, function (err, result) {
- if (err) {
- callback(err);
- return;
- }
-
- if (result === true) {
- loadDir(file, callback);
- } else {
- loadfile(file, callback);
- }
- });
- });
- });
- },
-
- //
- // the nodeunit driver class
- nodeunitDriver = function (moduleNames) {
- this.init(moduleNames);
- };
-
-// expose nodeunitDriver
-module.exports = nodeunitDriver;
-
-nodeunitDriver.prototype = {
- //
- // A dictionary of test names and their data.
- // each test has the following form:
- // {
- // testName: *THE NAME OF THE TEST*
- // metaData: *DATA REQUIRED IN ORDER TO RUN THE TEST*
- // }
- tests: {},
-
- //
- // Loads every node module appearing in modules
- // modules {object | array | string}: a nodeunit module | a path to nodeunit file | a path to a directory containing
- // nodeunit modules | an array containing any of the previous.
- init: function (modules) {
- var self = this,
- module,
- addTests = function (tests) {
- tests.forEach(function (test) {
- self.tests[test.testName] = test;
- console.log('adding test');
- });
- };
-
- // if modules is not an array
- if (typeof modules !== 'object' || !modules.length) {
- module = modules;
- modules = [];
- modules.push(module);
- }
-
- modules.forEach(function (module) {
- if (typeof module === 'string') {
- isDirectory(module, function (err, result) {
- if (err) {
- throw err;
- }
-
- if (result) {
- loadDir(module, addTests);
- } else {
- loadfile(module, addTests);
- }
- });
- } else {
- loadModule(module, addTests);
- }
- });
- },
-
- //
- // This method runs a test *testName* and calls the callback on the
- // test result. The callback on the test result upon completion.
- // testName {string}: The name of the test. must be a name generated by enumTests method
- // context {object}: Test context. Attached to each nodeunit test's 'test' parameter
- // callback {function}: A call back function called upon test completion and receiving the test
- // result as it's first argument
- runTest: function (testName, callback, context) {
- var test = this.tests[testName],
- testMethod,
- previousTestMethod;
-
- if (!test || !test.metadata) {
- callback('Failed to run test :"' + testName + '". Not on service');
- }
-
- testMethod = test.metadata;
-
- // add context if available
- if (context) {
- previousTestMethod = testMethod;
- testMethod = function (test) {
- test.context = context;
- previousTestMethod(test);
- };
- }
-
- reporter.run(testName, testMethod, callback);
- },
-
- //
- // applies *callback* on an array containing the tests names from testSuite.
- // assuming testSuite's functions are nodeunit style tests
- // callback {function}: A callback receiving the test names enumaration (array) as its second argument.
- enumTests: function (callback) {
- var testNames = [],
- key;
- for (key in this.tests) {
- if (this.tests.hasOwnProperty(key)) {
- testNames.push(this.tests[key].testName);
- }
- }
-
- callback(null, testNames);
- }
-};
Oops, something went wrong.

0 comments on commit 18e44e7

Please sign in to comment.