Migrate from nose to testr.

Run tests with testr for parallel execution.

Part of blueprint grizzly-testtools.

Change-Id: I38e8a2df12678002e19264a53bad26e80265c6e4
This commit is contained in:
Monty Taylor 2012-12-24 19:58:11 -06:00 committed by Josh Kearney
parent 53aee5cf4b
commit 7b2097e706
9 changed files with 84 additions and 58 deletions

2
.gitignore vendored
View File

@ -1,5 +1,7 @@
.coverage .coverage
.venv .venv
.testrepository
subunit.log
.tox .tox
*,cover *,cover
cover cover

4
.testr.conf Normal file
View File

@ -0,0 +1,4 @@
[DEFAULT]
test_command=OS_STDOUT_CAPTURE=1 OS_STDERR_CAPTURE=1 ${PYTHON:-python} -m subunit.run discover -t ./ ./tests $LISTOPT $IDOPTION
test_id_option=--load-list $IDFILE
test_list_option=--list

View File

@ -113,3 +113,11 @@ Text encoding
returntext = do_some_magic_with(mytext) returntext = do_some_magic_with(mytext)
returnstring = returntext.encode('utf-8') returnstring = returntext.encode('utf-8')
outfile.write(returnstring) outfile.write(returnstring)
Running Tests
-------------
The testing system is based on a combination of tox and testr. If you just
want to run the whole suite, run `tox` and all will be fine. However, if
you'd like to dig in a bit more, you might want to learn some things about
testr itself. A basic walkthrough for OpenStack can be found at
http://wiki.openstack.org/testr

View File

@ -33,8 +33,8 @@ function process_option {
-p|--pep8) just_pep8=1;; -p|--pep8) just_pep8=1;;
-P|--no-pep8) no_pep8=1;; -P|--no-pep8) no_pep8=1;;
-c|--coverage) coverage=1;; -c|--coverage) coverage=1;;
-*) noseopts="$noseopts $1";; -*) testropts="$testropts $1";;
*) noseargs="$noseargs $1" *) testrargs="$testrargs $1"
esac esac
} }
@ -45,34 +45,62 @@ never_venv=0
force=0 force=0
no_site_packages=0 no_site_packages=0
installvenvopts= installvenvopts=
noseargs= testrargs=
noseopts= testropts=
wrapper="" wrapper=""
just_pep8=0 just_pep8=0
no_pep8=0 no_pep8=0
coverage=0 coverage=0
LANG=en_US.UTF-8
LANGUAGE=en_US:en
LC_ALL=C
for arg in "$@"; do for arg in "$@"; do
process_option $arg process_option $arg
done done
# If enabled, tell nose to collect coverage data
if [ $coverage -eq 1 ]; then
noseopts="$noseopts --with-coverage --cover-package=novaclient"
fi
if [ $no_site_packages -eq 1 ]; then if [ $no_site_packages -eq 1 ]; then
installvenvopts="--no-site-packages" installvenvopts="--no-site-packages"
fi fi
function init_testr {
if [ ! -d .testrepository ]; then
${wrapper} testr init
fi
}
function run_tests { function run_tests {
# Cleanup *pyc
${wrapper} find . -type f -name "*.pyc" -delete
if [ $coverage -eq 1 ]; then
# Do not test test_coverage_ext when gathering coverage.
if [ "x$testrargs" = "x" ]; then
testrargs = "^(?!.*test_coverage_ext).*$"
fi
export PYTHON="${wrapper} coverage run --source novaclient --parallel-mode"
fi
# Just run the test suites in current environment # Just run the test suites in current environment
${wrapper} $NOSETESTS set +e
# If we get some short import error right away, print the error log directly TESTRTESTS="$TESTRTESTS $testrargs"
echo "Running \`${wrapper} $TESTRTESTS\`"
${wrapper} $TESTRTESTS
RESULT=$? RESULT=$?
set -e
copy_subunit_log
return $RESULT return $RESULT
} }
function copy_subunit_log {
LOGNAME=`cat .testrepository/next-stream`
LOGNAME=$(($LOGNAME - 1))
LOGNAME=".testrepository/${LOGNAME}"
cp $LOGNAME subunit.log
}
function run_pep8 { function run_pep8 {
echo "Running pep8 ..." echo "Running pep8 ..."
srcfiles="novaclient tests" srcfiles="novaclient tests"
@ -96,7 +124,7 @@ function run_pep8 {
${wrapper} pep8 ${pep8_opts} ${srcfiles} ${wrapper} pep8 ${pep8_opts} ${srcfiles}
} }
NOSETESTS="nosetests $noseopts $noseargs" TESTRTESTS="testr run --parallel $testropts"
if [ $never_venv -eq 0 ] if [ $never_venv -eq 0 ]
then then
@ -134,13 +162,14 @@ if [ $just_pep8 -eq 1 ]; then
exit exit
fi fi
init_testr
run_tests run_tests
# NOTE(sirp): we only want to run pep8 when we're running the full-test suite, # NOTE(sirp): we only want to run pep8 when we're running the full-test suite,
# not when we're running tests individually. To handle this, we need to # not when we're running tests individually. To handle this, we need to
# distinguish between options (noseopts), which begin with a '-', and # distinguish between options (noseopts), which begin with a '-', and
# arguments (noseargs). # arguments (testrargs).
if [ -z "$noseargs" ]; then if [ -z "$testrargs" ]; then
if [ $no_pep8 -eq 0 ]; then if [ $no_pep8 -eq 0 ]; then
run_pep8 run_pep8
fi fi
@ -148,5 +177,6 @@ fi
if [ $coverage -eq 1 ]; then if [ $coverage -eq 1 ]; then
echo "Generating coverage report in covhtml/" echo "Generating coverage report in covhtml/"
${wrapper} coverage html -d covhtml -i ${wrapper} cverage combine
${wrapper} coverage html --include='novaclient/*' --omit='novaclient/openstack/common/*' -d covhtml -i
fi fi

View File

@ -1,11 +1,3 @@
[nosetests]
cover-package = novaclient
cover-html = true
cover-erase = true
cover-inclusive = true
verbosity=2
detailed-errors=1
[build_sphinx] [build_sphinx]
source-dir = doc/source source-dir = doc/source
build-dir = doc/build build-dir = doc/build

View File

@ -34,7 +34,6 @@ setuptools.setup(
url="https://github.com/openstack/python-novaclient", url="https://github.com/openstack/python-novaclient",
packages=setuptools.find_packages(exclude=['tests', 'tests.*']), packages=setuptools.find_packages(exclude=['tests', 'tests.*']),
install_requires=setup.parse_requirements(), install_requires=setup.parse_requirements(),
test_suite="nose.collector",
cmdclass=setup.get_cmdclass(), cmdclass=setup.get_cmdclass(),
classifiers=[ classifiers=[
"Development Status :: 5 - Production/Stable", "Development Status :: 5 - Production/Stable",

View File

@ -1,3 +1,6 @@
import os
import fixtures
import requests import requests
import testtools import testtools
@ -8,6 +11,17 @@ class TestCase(testtools.TestCase):
'verify': True, 'verify': True,
} }
def setUp(self):
super(TestCase, self).setUp()
if (os.environ.get('OS_STDOUT_NOCAPTURE') == 'True' and
os.environ.get('OS_STDOUT_NOCAPTURE') == '1'):
stdout = self.useFixture(fixtures.StringStream('stdout')).stream
self.useFixture(fixtures.MonkeyPatch('sys.stdout', stdout))
if (os.environ.get('OS_STDERR_NOCAPTURE') == 'True' and
os.environ.get('OS_STDERR_NOCAPTURE') == '1'):
stderr = self.useFixture(fixtures.StringStream('stderr')).stream
self.useFixture(fixtures.MonkeyPatch('sys.stderr', stderr))
class TestResponse(requests.Response): class TestResponse(requests.Response):
""" """

View File

@ -1,12 +1,10 @@
distribute>=0.6.24 distribute>=0.6.24
fixtures coverage
discover
fixtures>=0.3.12
mock mock
nose
nose-exclude
nosexcover
openstack.nose_plugin
nosehtmloutput
pep8==1.1 pep8==1.1
sphinx>=1.1.2 sphinx>=1.1.2
testtools testrepository>=0.0.13
testtools>=0.9.26

33
tox.ini
View File

@ -3,14 +3,13 @@ envlist = py26,py27,pep8
[testenv] [testenv]
setenv = VIRTUAL_ENV={envdir} setenv = VIRTUAL_ENV={envdir}
NOSE_WITH_OPENSTACK=1 LANG=en_US.UTF-8
NOSE_OPENSTACK_COLOR=1 LANGUAGE=en_US:en
NOSE_OPENSTACK_RED=0.05 LC_ALL=C
NOSE_OPENSTACK_YELLOW=0.025
NOSE_OPENSTACK_SHOW_ELAPSED=1
deps = -r{toxinidir}/tools/pip-requires deps = -r{toxinidir}/tools/pip-requires
-r{toxinidir}/tools/test-requires -r{toxinidir}/tools/test-requires
commands = nosetests commands = python setup.py testr --testr-args='{posargs}'
[testenv:pep8] [testenv:pep8]
deps = pep8==1.1 deps = pep8==1.1
@ -20,27 +19,7 @@ commands = pep8 --repeat --show-source novaclient setup.py
commands = {posargs} commands = {posargs}
[testenv:cover] [testenv:cover]
commands = nosetests --cover-erase --cover-package=novaclient --with-xcoverage commands = python setup.py testr --coverage --testr-args='{posargs}'
[tox:jenkins] [tox:jenkins]
downloadcache = ~/cache/pip downloadcache = ~/cache/pip
[testenv:jenkins26]
basepython = python2.6
setenv = NOSE_WITH_XUNIT=1
deps = file://{toxinidir}/.cache.bundle
[testenv:jenkins27]
basepython = python2.7
setenv = NOSE_WITH_XUNIT=1
deps = file://{toxinidir}/.cache.bundle
[testenv:jenkinscover]
deps = file://{toxinidir}/.cache.bundle
setenv = NOSE_WITH_XUNIT=1
commands = nosetests --cover-erase --cover-package=novaclient --with-xcoverage
[testenv:jenkinsvenv]
deps = file://{toxinidir}/.cache.bundle
setenv = NOSE_WITH_XUNIT=1
commands = {posargs}