Unit tests
Here’s a few handy commands if you want to run only a specific unit test(s). Suppose we have the following unit tests in the project:
./gradlew test
– run unit tests for all variants
./gradlew testDebug
– run tests for Debug variant
./gradlew testDebug --tests="*.helpers.*"
– run all tests in the helpers
package
./gradlew testDebug --tests="*.HelperTest"
– run all tests in HelperTest.java
class
./gradlew testDebug --tests="*.getHelp"
– run only the getHelp
test method.
Instrumentation tests
Running instrumentation tests is a bit different than unit tests. If you just want to run a single instrumentation test class you can use:
./gradlew -Pandroid.testInstrumentationRunnerArguments.class=com.example.TestClass connectedDebugAndroidTest
Or if you want to run just 1 single test method within the class:
./gradlew -Pandroid.testInstrumentationRunnerArguments.class=com.example.TestClass#testMethod connectedDebugAndroidTest
There also another, more versatile way to run instrumentation tests from the console:
./gradlew installDebugAndroidTest
– install the app and tests
adb shell am instrument -w -e class com.example.MyInstrumentationTest#testFoo com.example.test/android.support.test.runner.AndroidJUnitRunner
The instrument
command supports a lot of options that give you fine-grained control over what and how it’s ran. For a full list of them check the official Android documentation HERE.
Bonus – printing unit test results to the console
It’s really useful to see why a unit test is failing directly in the console output like this:
To do so we need a bit of Gradle magic:
android { ... testOptions { unitTests.all { testLogging { events "passed", "failed", "standardError" showCauses true showExceptions true } } } }
Adding this to your build.gradle
will output the result of every test (passed / failed), or any errors that have occurred. Documentation for the testLogging
task, including all possible options can be found HERE.
One thing to mention here – by default Gradle will cache results of every task and won’t execute it again if there’s no changes (thus you see a lot of “UP-TO-DATE” when you run a subsequent build). This applies to the test
task as well, so running it twice in a row won’t run your unit tests twice if the first time is successful and you don’t perform a clean
in between.
If you want to overwrite the specific behaviour you can force the tests to be run every time by adding outputs.upToDateWhen {false}
to any task that’s part of the test
chain. Since you already have a testLogging
one in place, you can just put it there:
android { ... testOptions { unitTests.all { testLogging { outputs.upToDateWhen {false} events "passed", "failed", "standardError" showCauses true showExceptions true } } } }
Lastly it’s worth mentioning that if you have more specific needs in regards to running multiple test suites and configurations, it’s probably a good idea to take a look at Square’s Spoon or Shazam’s Fork libraries.
Happy testing!