venus.js
venus.js copied to clipboard
Add support for a @venus-execute annotation
When writing unit tests with venus, I've frequently needed to do some "setup" work before the test runs. Examples:
- Compile assets, such as dust templates, coffee-script files, or sass files.
- Copy files around, sometimes to make relative paths work correctly.
- Convert files, such changing a JSON file into a JavaScript file so I could load it with
@venus-resource.
Many of these are easy to do in server-side unit tests (e.g. JUnit), but they become tricky with the in-browser testing of Venus. My workaround so far has been to do these tasks in my build system (e.g. gradle or sbt), but this doesn't work with venus' hot reload and it makes the test harder to maintain and understand, since it's not clear that critical pieces live in some external build file.
What do you guys think about adding support for a @venus-execute annotation? You'd pass it the path of a JavaScript file and it would simply run it in node.js.
/**
* @venus-library mocha
* @venus-execute ../setup/setup.js
*/
describe("foo", function() {
it("Does stuff", function() {
expect(foo).to.be(bar);
});
});
The script could do any sort of setup you wanted. It would be much more flexible then adding more and more annotations for each custom use case. It makes the test code fairly standalone, more maintainable, and more readable.
Thoughts?
I think it's a great idea. Would you expect the script to run before each time the test runs (on reload of the test harness page, for example), or only when the test file or code under test changes?
For simplicity, probably run it every time this test file runs; since you don't know what the JS code will do, it's hard to say what dependencies it has that may change its output.
If you wanted to get fancier in the long term, most test frameworks support notions like before, after, before-suite, after-suite, etc. In theory, you could have @venus-execute-before-suite, @venus-execute-after-suite, etc... But I think that level of complexity is best saved until a use case for it comes along.
What if we simply enforce an interface for the files included by @venus-execute? Imagine something like:
@venus-execute setup.js
setup.js:
module.exports.before = function () {
// runs before all tests
};
module.exports.beforeEach = function () {
// runs before each test
};
module.exports.afterEach = function () {
// runs after each test
};
module.exports.after = function () {
// runs after all tests
};
I like it. Having such an API also gives room to pass some important parameters to the code:
module.exports.before = function (testFilePath) {
// runs before all tests
};
module.exports.beforeEach = function (testFilePath, testName) {
// runs before each test
};
Sounds good. I'll start on this today.
Got the before hook implemented. It's available on npm, version 2.3.0.
f2bf595
Sweet, thanks!