Estoy usando Android Studio/IntelliJ
para construir sobre un Android
proyecto existente y me gustaría agregar algunas JUnit
pruebas unitarias simples . ¿Cuál es la carpeta correcta para agregar tales pruebas?
El Gradle
complemento de Android define una estructura de directorio src/main/java
para el código fuente principal y src/instrumentTest/java
para las Android
pruebas.
Intentar agregar mis pruebas JUnit en instrumentTest no funcionó para mí. Puedo ejecutarlo como una Android
prueba (eso es lo que parece ese directorio) pero eso no es lo que estoy buscando, solo quiero ejecutar una JUnit
prueba simple . Intenté crear una configuración de ejecución JUnit para esta clase, pero tampoco funcionó; supongo que porque estoy usando un directorio que está marcado como Android
Prueba en lugar de Fuente.
Si creo una nueva carpeta de origen y la marco como tal en la Estructura del proyecto, esto se borrará la próxima vez que IntelliJ
actualice la configuración del proyecto desde los archivos de compilación de Gradle.
¿Cuál es la forma más adecuada de configurar las pruebas de JUnit en un proyecto de Android basado en gradle IntelliJ
? ¿Qué estructura de directorio usar para esto?
fuente
java.srcDirs = ['src/main/java','src/instrumentTest/java']
en lasourceSets
sección delbuild.gradle
/src/androidTest/java
carpeta predeterminada con pruebas de JUnit robolectric, ver: stackoverflow.com/a/25473702/1406325Respuestas:
A partir de Android Studio 1.1, la respuesta ahora es simple: http://tools.android.com/tech-docs/unit-testing-support
fuente
Normalmente, no puedes. Bienvenido al mundo de Android, donde todas las pruebas deben ejecutarse en un dispositivo (excepto Robolectric).
La razón principal es que en realidad no tiene las fuentes del marco; incluso si convence al IDE de que ejecute la prueba localmente, obtendrá inmediatamente una excepción "Stub! No implementado". "¿Por qué?" te preguntarás Porque lo
android.jar
que le brinda el SDK en realidad está desactivado: todas las clases y métodos están allí, pero todos simplemente lanzan una excepción. Está ahí para proporcionar una API, pero no para ofrecerle una implementación real.Hay un proyecto maravilloso llamado Robolectric que implementa gran parte del marco solo para que puedas ejecutar pruebas significativas. Junto con un buen marco simulado (por ejemplo, Mockito), hace que su trabajo sea manejable.
Complemento de Gradle: https://github.com/robolectric/robolectric-gradle-plugin
fuente
apply plugin: 'java'
), agregarlo a 'settings.gradle', tenerlo como una dependencia para su proyecto de Android (compile project(':plainJavaProjectName')
) y simplemente ejecutar latest
tarea. (¡No probado, pero definitivamente debería funcionar!)Intro
Tenga en cuenta que en el momento de escribir este artículo, robolectric 2.4 es la última versión y no tiene soporte para la
appcompat v7
biblioteca. Se agregará soporte en la versión robolectric 3.0 ( aún sin ETA ). TambiénActionBar Sherlock
puede causar problemas con robolectric.Para usar Robolectric dentro de Android Studio tienes 2 opciones:
(Opción 1): ejecutar pruebas JUnit con Android Studio usando un módulo Java
Esta técnica utiliza un módulo de Java para todas sus pruebas con una dependencia a su módulo de Android y un corredor de prueba personalizado con algo de magia:
Las instrucciones se pueden encontrar aquí: http://blog.blundellapps.com/how-to-run-robolectric-junit-tests-in-android-studio/
También verifique el enlace al final de esa publicación para ejecutar las pruebas desde Android Studio.
(Opción 2) - Ejecutar pruebas JUnit con Android Studio usando robolectric-gradle-plugin
Encontré algunos problemas al configurar las pruebas junit para que se ejecuten desde gradle en Android Studio.
Este es un proyecto de muestra muy básico para ejecutar pruebas junit desde un proyecto basado en gradle en Android Studio: https://github.com/hanscappelle/android-studio-junit-robolectric Esto se probó con Android Studio 0.8.14, JUnit 4.10, complemento Gradle robolectric 0.13+ y robolectric 2.3
Buildscript (proyecto / build.gradle)
El script de compilación es el archivo build.gradle en la raíz de su proyecto. Allí tuve que agregar el complemento Gradle robolectric a classpath
buildscript { repositories { jcenter() } dependencies { classpath 'com.android.tools.build:gradle:0.13.2' // NOTE: Do not place your application dependencies here; they belong // in the individual module build.gradle files classpath 'org.robolectric:robolectric-gradle-plugin:0.13.+' } } allprojects { repositories { jcenter() } }
Proyecto buildscript (App / build.gradle)
En el script de compilación del módulo de su aplicación, use el
robolectric
complemento, agregue larobolectric
configuración y agregue lasandroidTestCompile
dependencias.apply plugin: 'com.android.application' apply plugin: 'robolectric' android { // like any other project } robolectric { // configure the set of classes for JUnit tests include '**/*Test.class' exclude '**/espresso/**/*.class' // configure max heap size of the test JVM maxHeapSize = '2048m' // configure the test JVM arguments jvmArgs '-XX:MaxPermSize=512m', '-XX:-UseSplitVerifier' // configure whether failing tests should fail the build ignoreFailures true // use afterTest to listen to the test execution results afterTest { descriptor, result -> println "Executing test for {$descriptor.name} with result: ${result.resultType}" } } dependencies { compile fileTree(dir: 'libs', include: ['*.jar']) androidTestCompile 'org.robolectric:robolectric:2.3' androidTestCompile 'junit:junit:4.10' }
Crear clases de prueba JUnit
Ahora coloque las clases de prueba en la ubicación predeterminada (o actualice la configuración de gradle)
Y asigne un nombre a sus clases de pruebas que terminen con Test (o actualice nuevamente la configuración), ampliando
junit.framework.TestCase
y anote los métodos de prueba con@Test
.package be.hcpl.android.mytestedapplication; import junit.framework.TestCase; import org.junit.Test; public class MainActivityTest extends TestCase { @Test public void testThatSucceeds(){ // all OK assert true; } @Test public void testThatFails(){ // all NOK assert false; } }
Ejecutar pruebas
Luego, ejecute las pruebas usando gradlew desde la línea de comando (hágalo ejecutable usando
chmod +x
si es necesario)./gradlew clean test
Salida de muestra:
Executing test for {testThatSucceeds} with result: SUCCESS Executing test for {testThatFails} with result: FAILURE android.hcpl.be.mytestedapplication.MainActivityTest > testThatFails FAILED java.lang.AssertionError at MainActivityTest.java:21 2 tests completed, 1 failed There were failing tests. See the report at: file:///Users/hcpl/Development/git/MyTestedApplication/app/build/test-report/debug/index.html :app:test BUILD SUCCESSFUL
Solución de problemas
directorios de fuentes alternativas
Al igual que puede tener sus archivos fuente de Java en otro lugar, puede mover sus archivos fuente de prueba. Simplemente actualice la
sourceSets
configuración de gradle .sourceSets { main { manifest.srcFile 'AndroidManifest.xml' java.srcDirs = ['src'] res.srcDirs = ['res'] assets.srcDirs = ['assets'] } androidTest { setRoot('tests') } }
el paquete org.junit no existe
Olvidó agregar la dependencia de prueba junit en el script de compilación de la aplicación
dependencies { compile fileTree(dir: 'libs', include: ['*.jar']) androidTestCompile 'org.robolectric:robolectric:2.3' androidTestCompile 'junit:junit:4.10' }
java.lang.RuntimeException: Stub!
Está ejecutando esta prueba con las configuraciones de ejecución de Android Studio en lugar de la línea de comandos (pestaña Terminal en Android Studio). Para ejecutarlo desde Android Studio, deberá actualizar el
app.iml
archivo para que la entrada jdk aparezca en la parte inferior. Consulte el ejemplo de deckard-gradle para obtener más detalles.Ejemplo de error completo:
!!! JUnit version 3.8 or later expected: java.lang.RuntimeException: Stub! at junit.runner.BaseTestRunner.<init>(BaseTestRunner.java:5) at junit.textui.TestRunner.<init>(TestRunner.java:54) at junit.textui.TestRunner.<init>(TestRunner.java:48) at junit.textui.TestRunner.<init>(TestRunner.java:41) at com.intellij.rt.execution.junit.JUnitStarter.junitVersionChecks(JUnitStarter.java:190) at com.intellij.rt.execution.junit.JUnitStarter.canWorkWithJUnitVersion(JUnitStarter.java:173) at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:56) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.lang.reflect.Method.invoke(Method.java:606) at com.intellij.rt.execution.application.AppMain.main(AppMain.java:134)
ERROR: JAVA_HOME está configurado en un directorio no válido
Consulte esta pregunta SO para obtener una solución. Agregue la siguiente exportación a su perfil de bash:
export JAVA_HOME=`/usr/libexec/java_home -v 1.7`
El registro de errores completo:
ERROR: JAVA_HOME is set to an invalid directory: export JAVA_HOME=/Library/Java/JavaVirtualMachines/jdk1.7.0_51.jdk/Contents/Home Please set the JAVA_HOME variable in your environment to match the location of your Java installation.
Clase de prueba no encontrada
Si desea ejecutar sus pruebas desde Android Studio Junit Test runner, tendrá que expandir el archivo build.gradle un poco más para que Android Studio pueda encontrar sus clases de prueba compiladas:
sourceSets { testLocal { java.srcDir file('src/test/java') resources.srcDir file('src/test/resources') } } android { // tell Android studio that the instrumentTest source set is located in the unit test source set sourceSets { instrumentTest.setRoot('src/test') } } dependencies { // Dependencies for the `testLocal` task, make sure to list all your global dependencies here as well testLocalCompile 'junit:junit:4.11' testLocalCompile 'com.google.android:android:4.1.1.4' testLocalCompile 'org.robolectric:robolectric:2.3' // Android Studio doesn't recognize the `testLocal` task, so we define the same dependencies as above for instrumentTest // which is Android Studio's test task androidTestCompile 'junit:junit:4.11' androidTestCompile 'com.google.android:android:4.1.1.4' androidTestCompile 'org.robolectric:robolectric:2.3' } task localTest(type: Test, dependsOn: assemble) { testClassesDir = sourceSets.testLocal.output.classesDir android.sourceSets.main.java.srcDirs.each { dir -> def buildDir = dir.getAbsolutePath().split('/') buildDir = (buildDir[0..(buildDir.length - 4)] + ['build', 'classes', 'debug']).join('/') sourceSets.testLocal.compileClasspath += files(buildDir) sourceSets.testLocal.runtimeClasspath += files(buildDir) } classpath = sourceSets.testLocal.runtimeClasspath } check.dependsOn localTest
de: http://kostyay.name/android-studio-robolectric-gradle-getting-work/
Algunos recursos más
Los mejores artículos que encontré sobre esto son:
fuente
Esto ahora es compatible con Android Studio a partir del complemento de Android Gradle 1.1.0, mira esto:
https://developer.android.com/training/testing/unit-testing/local-unit-tests.html
Aplicación de muestra con pruebas de unidades locales en GitHub:
https://github.com/googlesamples/android-testing/tree/master/unittesting/BasicSample
fuente
Para Android Studio 1.2+, configurar un proyecto para JUnit es bastante simple, intente seguir este tutorial:
Esta es la parte más simple de configurar un proyecto para JUnit:
https://io2015codelabs.appspot.com/codelabs/android-studio-testing#1
Siga el enlace anterior hasta " Ejecutar sus pruebas ".
Ahora, si desea integrarse con la prueba de instrumentación, siga desde aquí:
https://io2015codelabs.appspot.com/codelabs/android-studio-testing#6
fuente
Consulte este tutorial del sitio oficial de desarrolladores de Android. Este artículo también muestra cómo crear maquetas para sus pruebas.
Por cierto, debe tener en cuenta que el alcance de las dependencias para la prueba JUnit simple debe ser "testCompile".
fuente