Unit testing infrastructure
Implements the beginnings of unit testing infrastructure using mocha/chai. The unit tests can be run locally using test/runtests.sh, although this will need tweaks to run on Windows. They should also run on commit using Travis-CI. The unit tests themselves live in test/tests. The index.js file specifies separate test sets, which can be run individually by calling test/runtests.sh <testsets>. Right now there is only a single unit test, but hopefully we'll have more soon...
This commit is contained in:
parent
5285fadded
commit
1c32db68da
12 changed files with 289 additions and 0 deletions
6
.gitmodules
vendored
6
.gitmodules
vendored
|
@ -7,3 +7,9 @@
|
|||
[submodule "styles"]
|
||||
path = styles
|
||||
url = git://github.com/zotero/bundled-styles.git
|
||||
[submodule "test/resource/chai"]
|
||||
path = test/resource/chai
|
||||
url = https://github.com/chaijs/chai.git
|
||||
[submodule "test/resource/mocha"]
|
||||
path = test/resource/mocha
|
||||
url = https://github.com/mochajs/mocha.git
|
||||
|
|
16
.travis.yml
Normal file
16
.travis.yml
Normal file
|
@ -0,0 +1,16 @@
|
|||
language: cpp
|
||||
compiler:
|
||||
- gcc
|
||||
env:
|
||||
matrix:
|
||||
- FIREFOXVERSION="36.0.1"
|
||||
- FIREFOXVERSION="31.5.0esr"
|
||||
notifications:
|
||||
email: false
|
||||
before_install:
|
||||
- export DISPLAY=:99.0
|
||||
- sh -e /etc/init.d/xvfb start
|
||||
- wget http://ftp.mozilla.org/pub/firefox/releases/${FIREFOXVERSION}/linux-x86_64/en-US/firefox-${FIREFOXVERSION}.tar.bz2
|
||||
- tar -xjf firefox-${FIREFOXVERSION}.tar.bz2
|
||||
script:
|
||||
- test/runtests.sh -x firefox/firefox
|
7
test/chrome.manifest
Normal file
7
test/chrome.manifest
Normal file
|
@ -0,0 +1,7 @@
|
|||
content zotero-unit content/
|
||||
resource zotero-unit resource/
|
||||
resource zotero-unit-tests tests/
|
||||
|
||||
component {b8570031-be5e-46e8-9785-38cd50a5d911} components/zotero-unit.js
|
||||
contract @mozilla.org/commandlinehandler/general-startup;1?type=zotero-unit {b8570031-be5e-46e8-9785-38cd50a5d911}
|
||||
category command-line-handler m-zotero-unit @mozilla.org/commandlinehandler/general-startup;1?type=zotero-unit
|
51
test/components/zotero-unit.js
Normal file
51
test/components/zotero-unit.js
Normal file
|
@ -0,0 +1,51 @@
|
|||
"use strict";
|
||||
/*
|
||||
***** BEGIN LICENSE BLOCK *****
|
||||
|
||||
Copyright © 2012 Center for History and New Media
|
||||
George Mason University, Fairfax, Virginia, USA
|
||||
http://zotero.org
|
||||
|
||||
This file is part of Zotero.
|
||||
|
||||
Zotero is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
Zotero is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with Zotero. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
***** END LICENSE BLOCK *****
|
||||
*/
|
||||
Components.utils.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
function ZoteroUnit() {
|
||||
this.wrappedJSObject = this;
|
||||
}
|
||||
ZoteroUnit.prototype = {
|
||||
/* nsICommandLineHandler */
|
||||
handle:function(cmdLine) {
|
||||
this.tests = cmdLine.handleFlagWithParam("test", false);
|
||||
},
|
||||
|
||||
dump:function(x) {
|
||||
dump(x);
|
||||
},
|
||||
|
||||
contractID: "@mozilla.org/commandlinehandler/general-startup;1?type=zotero-unit",
|
||||
classDescription: "Zotero Unit Command Line Handler",
|
||||
classID: Components.ID("{b8570031-be5e-46e8-9785-38cd50a5d911}"),
|
||||
service: true,
|
||||
_xpcom_categories: [{category:"command-line-handler", entry:"m-zotero-unit"}],
|
||||
QueryInterface: XPCOMUtils.generateQI([Components.interfaces.nsICommandLineHandler,
|
||||
Components.interfaces.nsISupports])
|
||||
};
|
||||
|
||||
|
||||
var NSGetFactory = XPCOMUtils.generateNSGetFactory([ZoteroUnit]);
|
14
test/content/runtests.html
Normal file
14
test/content/runtests.html
Normal file
|
@ -0,0 +1,14 @@
|
|||
<html>
|
||||
<head>
|
||||
<meta charset="utf-8"></meta>
|
||||
<title>Zotero Unit Tests</title>
|
||||
</head>
|
||||
<body>
|
||||
<script src="jquery.js"></script>
|
||||
<script src="chrome://zotero/content/include.js"></script>
|
||||
<script src="resource://zotero-unit/chai/chai.js"></script>
|
||||
<script src="resource://zotero-unit/mocha/mocha.js"></script>
|
||||
<script src="resource://zotero-unit-tests/index.js"></script>
|
||||
<script src="runtests.js" version="application/javascript;version=1.8"></script>
|
||||
</body>
|
||||
</html>
|
88
test/content/runtests.js
Normal file
88
test/content/runtests.js
Normal file
|
@ -0,0 +1,88 @@
|
|||
Components.utils.import("resource://gre/modules/FileUtils.jsm");
|
||||
Components.utils.import("resource://gre/modules/osfile.jsm")
|
||||
|
||||
var ZoteroUnit = Components.classes["@mozilla.org/commandlinehandler/general-startup;1?type=zotero-unit"].
|
||||
getService(Components.interfaces.nsISupports).
|
||||
wrappedJSObject;
|
||||
var dump = ZoteroUnit.dump;
|
||||
|
||||
function quit(failed) {
|
||||
// Quit with exit status
|
||||
if(!failed) {
|
||||
OS.File.writeAtomic(FileUtils.getFile("ProfD", ["success"]).path, Uint8Array(0));
|
||||
}
|
||||
Components.classes['@mozilla.org/toolkit/app-startup;1'].
|
||||
getService(Components.interfaces.nsIAppStartup).
|
||||
quit(Components.interfaces.nsIAppStartup.eForceQuit);
|
||||
}
|
||||
|
||||
function Reporter(runner) {
|
||||
var indents = 0, passed = 0, failed = 0;
|
||||
|
||||
function indent() {
|
||||
return Array(indents).join(' ');
|
||||
}
|
||||
|
||||
runner.on('start', function(){});
|
||||
|
||||
runner.on('suite', function(suite){
|
||||
++indents;
|
||||
dump(indent()+suite.title+"\n");
|
||||
});
|
||||
|
||||
runner.on('suite end', function(suite){
|
||||
--indents;
|
||||
if (1 == indents) dump("\n");
|
||||
});
|
||||
|
||||
runner.on('pending', function(test){
|
||||
dump(indent()+"pending -"+test.title);
|
||||
});
|
||||
|
||||
runner.on('pass', function(test){
|
||||
passed++;
|
||||
var msg = "\r"+indent()+Mocha.reporters.Base.symbols.ok+" "+test.title;
|
||||
if ('fast' != test.speed) {
|
||||
msg += " ("+Math.round(test.duration)+" ms)";
|
||||
}
|
||||
dump(msg+"\n");
|
||||
});
|
||||
|
||||
runner.on('fail', function(test, err){
|
||||
failed++;
|
||||
dump("\r"+indent()+Mocha.reporters.Base.symbols.err+" "+test.title+"\n");
|
||||
});
|
||||
|
||||
runner.on('end', function() {
|
||||
dump(passed+"/"+(passed+failed)+" tests passed.\n");
|
||||
quit(failed != 0);
|
||||
});
|
||||
}
|
||||
|
||||
// Setup Mocha
|
||||
mocha.setup({ui:"bdd", reporter:Reporter});
|
||||
var assert = chai.assert,
|
||||
expect = chai.expect;
|
||||
|
||||
// Set up tests to run
|
||||
if(ZoteroUnit.tests) {
|
||||
document.body.appendChild(document.createTextNode("Running tests..."));
|
||||
var torun = ZoteroUnit.tests == "all" ? Object.keys(TESTS) : ZoteroUnit.tests.split(",");
|
||||
|
||||
for(var key of torun) {
|
||||
if(!TESTS[key]) {
|
||||
dump("Invalid test set "+torun+"\n");
|
||||
quit(true);
|
||||
}
|
||||
for(var test of TESTS[key]) {
|
||||
var el = document.createElement("script");
|
||||
el.type = "application/javascript;version=1.8";
|
||||
el.src = "resource://zotero-unit-tests/"+test;
|
||||
document.body.appendChild(el);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
window.onload = function() {
|
||||
mocha.run();
|
||||
};
|
26
test/install.rdf
Normal file
26
test/install.rdf
Normal file
|
@ -0,0 +1,26 @@
|
|||
<?xml version="1.0"?>
|
||||
<RDF xmlns="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:em="http://www.mozilla.org/2004/em-rdf#">
|
||||
|
||||
<Description about="urn:mozilla:install-manifest">
|
||||
|
||||
<em:id>zotero-unit@zotero.org</em:id>
|
||||
<em:name>Zotero Unit Tests</em:name>
|
||||
<em:version>1.0</em:version>
|
||||
<em:creator>Center for History and New Media</em:creator>
|
||||
<em:developer>Simon Kornblith</em:developer>
|
||||
<em:homepageURL>http://www.zotero.org</em:homepageURL>
|
||||
<em:iconURL>chrome://zotero/skin/zotero-new-z-48px.png</em:iconURL>
|
||||
<em:type>2</em:type> <!-- type=extension -->
|
||||
|
||||
<!-- Firefox -->
|
||||
<em:targetApplication>
|
||||
<Description>
|
||||
<em:id>{ec8030f7-c20a-464f-9b0e-13a3a9e97384}</em:id>
|
||||
<em:minVersion>31.0</em:minVersion>
|
||||
<em:maxVersion>38.*</em:maxVersion>
|
||||
</Description>
|
||||
</em:targetApplication>
|
||||
|
||||
</Description>
|
||||
</RDF>
|
1
test/resource/chai
Submodule
1
test/resource/chai
Submodule
|
@ -0,0 +1 @@
|
|||
Subproject commit d7cafca0232756f767275bb00e66930a7823b027
|
1
test/resource/mocha
Submodule
1
test/resource/mocha
Submodule
|
@ -0,0 +1 @@
|
|||
Subproject commit 65fc80ecd96ca2159a792aff089bbc273d4bd86d
|
56
test/runtests.sh
Executable file
56
test/runtests.sh
Executable file
|
@ -0,0 +1,56 @@
|
|||
#!/bin/bash
|
||||
CWD="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
|
||||
|
||||
if [ "`uname`" == "Darwin" ]; then
|
||||
FX_EXECUTABLE="/Applications/Firefox.app/Contents/MacOS/firefox"
|
||||
else
|
||||
FX_EXECUTABLE="firefox"
|
||||
fi
|
||||
|
||||
function usage {
|
||||
cat >&2 <<DONE
|
||||
Usage: $0 [-x FX_EXECUTABLE] [TESTS...]
|
||||
Options
|
||||
-x FX_EXECUTABLE path to Firefox executable (default: $FX_EXECUTABLE)
|
||||
TESTS set of tests to run (default: all)
|
||||
DONE
|
||||
exit 1
|
||||
}
|
||||
|
||||
while getopts "x:" opt; do
|
||||
case $opt in
|
||||
x)
|
||||
FX_EXECUTABLE="$OPTARG"
|
||||
;;
|
||||
*)
|
||||
usage
|
||||
;;
|
||||
esac
|
||||
shift $((OPTIND-1)); OPTIND=1
|
||||
done
|
||||
|
||||
if [ -z $1 ]; then
|
||||
TESTS="all"
|
||||
else
|
||||
ARGS=("${@:1}")
|
||||
function join { local IFS="$1"; shift; echo "$*"; }
|
||||
TESTS="$(join , "${ARGS[@]}")"
|
||||
fi
|
||||
|
||||
# Set up profile directory
|
||||
PROFILE="`mktemp -d 2>/dev/null || mktemp -d -t 'zotero-unit'`"
|
||||
mkdir "$PROFILE/extensions"
|
||||
echo "$CWD" > "$PROFILE/extensions/zotero-unit@zotero.org"
|
||||
echo "`dirname "$CWD"`" > "$PROFILE/extensions/zotero@chnm.gmu.edu"
|
||||
echo 'user_pref("extensions.autoDisableScopes", 0);' > "$PROFILE/prefs.js"
|
||||
|
||||
MOZ_NO_REMOTE=1 NO_EM_RESTART=1 "$FX_EXECUTABLE" -profile "$PROFILE" \
|
||||
-chrome chrome://zotero-unit/content/runtests.html -test "$TESTS"
|
||||
|
||||
# Check for success
|
||||
test -e "$PROFILE/success"
|
||||
STATUS=$?
|
||||
|
||||
# Clean up
|
||||
rm -rf "$PROFILE"
|
||||
exit $STATUS
|
3
test/tests/index.js
Normal file
3
test/tests/index.js
Normal file
|
@ -0,0 +1,3 @@
|
|||
var TESTS = {
|
||||
"utilities":["utilities.js"]
|
||||
};
|
20
test/tests/utilities.js
Normal file
20
test/tests/utilities.js
Normal file
|
@ -0,0 +1,20 @@
|
|||
describe("Zotero.Utilities", function() {
|
||||
describe("cleanAuthor", function() {
|
||||
it('should parse author names', function() {
|
||||
for(let useComma of [false, true]) {
|
||||
for(let first_expected of [["First", "First"],
|
||||
["First Middle", "First Middle"],
|
||||
["F. R. S.", "F. R. S."],
|
||||
["F.R.S.", "F. R. S."],
|
||||
["F R S", "F. R. S."],
|
||||
["FRS", "F. R. S."]]) {
|
||||
let [first, expected] = first_expected;
|
||||
let str = useComma ? "Last, "+first : first+" Last";
|
||||
let author = Zotero.Utilities.cleanAuthor(str, "author", useComma);
|
||||
assert.equal(author.firstName, expected);
|
||||
assert.equal(author.lastName, "Last");
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
Loading…
Reference in a new issue