diff --git a/.gitignore b/.gitignore
index ed95d1137597d9be28a656083ddf4bb259c95dab..17ed160808f0be8e8b8eb907138b10fec550ca39 100644
--- a/.gitignore
+++ b/.gitignore
@@ -25,8 +25,7 @@ pip-log.txt
 .tox
 cover
 cover-master
-nosetests.xml
-.testrepository
+.stestr/
 .venv
 
 # Translations
diff --git a/.stestr.conf b/.stestr.conf
new file mode 100644
index 0000000000000000000000000000000000000000..8189a278d5273ec663d8cb0f382a77877081ea7b
--- /dev/null
+++ b/.stestr.conf
@@ -0,0 +1,3 @@
+[DEFAULT]
+test_path=${OS_TEST_PATH:-./}
+top_dir=./
diff --git a/.testr.conf b/.testr.conf
deleted file mode 100644
index 6d83b3c4ec569285143d929e8239c99cdffa8eb4..0000000000000000000000000000000000000000
--- a/.testr.conf
+++ /dev/null
@@ -1,7 +0,0 @@
-[DEFAULT]
-test_command=OS_STDOUT_CAPTURE=${OS_STDOUT_CAPTURE:-1} \
-             OS_STDERR_CAPTURE=${OS_STDERR_CAPTURE:-1} \
-             OS_TEST_TIMEOUT=${OS_TEST_TIMEOUT:-60} \
-             ${PYTHON:-python} -m subunit.run discover -t ./ . $LISTOPT $IDOPTION
-test_id_option=--load-list $IDFILE
-test_list_option=--list
diff --git a/lower-constraints.txt b/lower-constraints.txt
index 0d4f5051bcd33eca09bd7b8f63466ee08895c6fa..e989e5659e0323f26eaacca2609063e245d21667 100644
--- a/lower-constraints.txt
+++ b/lower-constraints.txt
@@ -103,7 +103,7 @@ sphinxcontrib-websupport==1.0.1
 statsd==3.2.1
 stevedore==1.20.0
 tenacity==3.2.1
-testrepository==0.0.18
+stestr==2.0.0
 testscenarios==0.4
 testtools==2.2.0
 traceback2==1.4.0
diff --git a/requirements.txt b/requirements.txt
index 87eb582662e87deacbcb8889503310ce423cb4c1..230787bc39f0b336a81d31a49d609051eb609382 100644
--- a/requirements.txt
+++ b/requirements.txt
@@ -5,7 +5,7 @@ pbr!=2.1.0,>=2.0.0 # Apache-2.0
 
 Babel!=2.4.0,>=2.3.4 # BSD
 six>=1.10.0 # MIT
-keystoneauth1>=3.3.0 # Apache-2.0
+keystoneauth1>=3.4.0 # Apache-2.0
 stevedore>=1.20.0 # Apache-2.0
 requests>=2.14.2 # Apache-2.0
 oslo.i18n>=3.15.3 # Apache-2.0
@@ -14,6 +14,6 @@ oslo.serialization!=2.19.1,>=2.18.0 # Apache-2.0
 oslo.utils>=3.33.0 # Apache-2.0
 os-client-config>=1.28.0 # Apache-2.0
 osc-lib>=1.8.0 # Apache-2.0
-PrettyTable<0.8,>=0.7.1 # BSD
-cryptography!=2.0,>=1.9 # BSD/Apache-2.0
+PrettyTable<0.8,>=0.7.2 # BSD
+cryptography>=2.1 # BSD/Apache-2.0
 decorator>=3.4.0 # BSD
diff --git a/test-requirements.txt b/test-requirements.txt
index 72fed3f45678bbd470caefbe26c56f9adaea3c49..f625855cb8f3a8e008d678ebd34bd4ed56a857b4 100644
--- a/test-requirements.txt
+++ b/test-requirements.txt
@@ -8,7 +8,7 @@ fixtures>=3.0.0 # Apache-2.0/BSD
 python-openstackclient>=3.12.0 # Apache-2.0
 oslotest>=3.2.0 # Apache-2.0
 osprofiler>=1.4.0 # Apache-2.0
-testrepository>=0.0.18 # Apache-2.0/BSD
+stestr>=2.0.0 # Apache-2.0
 testscenarios>=0.4 # Apache-2.0/BSD
 testtools>=2.2.0 # MIT
 mock>=2.0.0 # BSD
diff --git a/tools/cover.sh b/tools/cover.sh
index 42baf5d8e61585f1fe20710c95360316494a8d40..74b25d9b5db63edc4ac3e9cde5b84ecd4e0da62e 100755
--- a/tools/cover.sh
+++ b/tools/cover.sh
@@ -30,7 +30,12 @@ fi
 git checkout HEAD^
 
 baseline_report=$(mktemp -t magnumclient_coverageXXXXXXX)
-find . -type f -name "*.pyc" -delete && python setup.py testr --coverage --testr-args="$*"
+find . -type f -name "*.pyc" -delete
+stestr run "$*"
+coverage combine
+coverage report --fail-under=80 --skip-covered
+coverage html -d cover
+coverage xml -o cover/coverage.xml
 coverage report > $baseline_report
 mv cover cover-master
 cat $baseline_report
@@ -40,7 +45,12 @@ baseline_missing=$(awk 'END { print $3 }' $baseline_report)
 git checkout -
 
 current_report=$(mktemp -t magnumclient_coverageXXXXXXX)
-find . -type f -name "*.pyc" -delete && python setup.py testr --coverage --testr-args="$*"
+find . -type f -name "*.pyc" -delete
+stestr run "$*"
+coverage combine
+coverage report --fail-under=80 --skip-covered
+coverage html -d cover
+coverage xml -o cover/coverage.xml
 coverage report > $current_report
 current_missing=$(awk 'END { print $3 }' $current_report)
 
diff --git a/tox.ini b/tox.ini
index c089277b9fa62776975b747625c9d97932e4db54..0d4aaff4903d4c428f453dad3497e0c25d841c18 100644
--- a/tox.ini
+++ b/tox.ini
@@ -16,7 +16,7 @@ deps =
        -r{toxinidir}/test-requirements.txt
 commands =
   find . -type f -name "*.py[c|o]" -delete
-  python setup.py testr --slowest --testr-args='{posargs}'
+  stestr run --slowest {posargs}
 
 [testenv:bandit]
 basepython = python3