AndroidJUnitRunner

A classe AndroidJUnitRunner é um executor de testes do JUnit (em inglês) que permite executar classes de testes no estilo do JUnit 3 ou do JUnit 4 em dispositivos Android, incluindo aquelas que usam os frameworks de teste Espresso e UI Automator.

O executor de testes processa o carregamento do pacote e do app em questão em um dispositivo, a execução dos testes e o relatório de resultados. Essa classe substitui a InstrumentationTestRunner, que é compatível apenas com testes do JUnit 3.

Este executor é compatível com várias tarefas de teste comuns, entre elas:

Programar testes do JUnit

O executor é compatível com testes do JUnit 3 e do JUnit 4 (até o JUnit 4.10). No entanto, evite misturar código de testes JUnit 3 e JUnit 4 no mesmo pacote, porque isso pode causar resultados inesperados. Se você está criando uma classe de teste de instrumentação do JUnit 4 para ser executada em um dispositivo ou emulador, ela precisa ser prefixada com a anotação @RunWith(AndroidJUnit4.class).

O snippet de código a seguir mostra como programar um teste de instrumentação do JUnit 4 para verificar se a operação changeText na classe ChangeTextBehavior funciona corretamente.

Kotlin

    @RunWith(AndroidJUnit4::class)
    @LargeTest
    class ChangeTextBehaviorTest {
        val stringToBeTyped = "Espresso"
        @get:Rule
        val activityRule = ActivityTestRule(MainActivity::class.java)

        @Test fun changeText_sameActivity() {
            // Type text and then press the button.
            onView(withId(R.id.editTextUserInput))
                .perform(typeText(stringToBeTyped), closeSoftKeyboard())
            onView(withId(R.id.changeTextBt)).perform(click())

            // Check that the text was changed.
            onView(withId(R.id.textToBeChanged))
                .check(matches(withText(stringToBeTyped)))
        }
    }
    

Java

    @RunWith(AndroidJUnit4.class)
    @LargeTest
    public class ChangeTextBehaviorTest {

        private static final String stringToBeTyped = "Espresso";

        @Rule
        public ActivityTestRule<MainActivity> activityRule =
                new ActivityTestRule<>(MainActivity.class);

        @Test
        public void changeText_sameActivity() {
            // Type text and then press the button.
            onView(withId(R.id.editTextUserInput))
                    .perform(typeText(stringToBeTyped), closeSoftKeyboard());
            onView(withId(R.id.changeTextBt)).perform(click());

            // Check that the text was changed.
            onView(withId(R.id.textToBeChanged))
                    .check(matches(withText(stringToBeTyped)));
        }
    }
    

Usar o Android Test Orchestrator

Ao usar o AndroidJUnitRunner versão 1.0 ou posterior, você tem acesso à ferramenta Android Test Orchestrator, que permite executar cada teste do app com a própria invocação de Instrumentation.

O Android Test Orchestrator oferece as seguintes vantagens para seu ambiente de teste:

  • Estado compartilhado mínimo. Cada teste é executado na própria instância Instrumentation. Assim, se seus testes compartilham o estado do app, a maior parte desse estado compartilhado é removida da CPU ou da memória do dispositivo depois de cada teste.

    Para remover todo o estado compartilhado da CPU e da memória do dispositivo depois de cada teste, use a sinalização clearPackageData.

  • Falhas isoladas. Mesmo se um teste falhar, ele interromperá apenas a própria instância de Instrumentation. Assim, os outros testes do conjunto continuarão sendo executados.

O Android Studio e o Firebase Test Lab vêm com o Android Test Orchestrator pré-instalado, embora você precise ativar o recurso no Android Studio.

No entanto, se você usa outro conjunto de ferramentas para testar o app, ainda pode usar o Android Test Orchestrator seguindo estas etapas:

  1. Inclua os pacotes necessários no arquivo de compilação do app.
  2. Ative o Android Test Orchestrator na linha de comando.

Ativar no Gradle

Para ativar o Android Test Orchestrator usando a ferramenta de linha de comando do Gradle, siga estas etapas:

  1. Adicione as seguintes declarações ao arquivo build.gradle do projeto:

        android {
          defaultConfig {
           ...
           testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
    
           // The following argument makes the Android Test Orchestrator run its
           // "pm clear" command after each test invocation. This command ensures
           // that the app's state is completely cleared between tests.
           testInstrumentationRunnerArguments clearPackageData: 'true'
         }
    
          testOptions {
            execution 'ANDROIDX_TEST_ORCHESTRATOR'
          }
        }
    
        dependencies {
          androidTestImplementation 'androidx.test:runner:1.1.0'
          androidTestUtil 'androidx.test:orchestrator:1.1.0'
        }
  2. Execute o Android Test Orchestrator com este comando:

        ./gradlew connectedCheck

Ativar no Android Studio

A compatibilidade com o Android Test Orchestrator está disponível no Android Studio 3.0 e posteriores. Para ativar o Android Test Orchestrator no Android Studio, adicione as declarações mostradas em Ativar no Gradle ao arquivo build.gradle do app.

Ativar na linha de comando

Para usar o Android Test Orchestrator na linha de comando, execute os seguintes comandos em uma janela de terminal:

    # Install the test orchestrator.
    adb install -r path/to/m2repository/androidx/test/orchestrator/1.1.0/orchestrator-1.1.0.apk

    # Install test services.
    adb install -r path/to/m2repository/androidx/test/services/test-services/1.1.0/test-services-1.1.0.apk

    # Replace "com.example.test" with the name of the package containing your tests.
    # Add "-e clearPackageData true" to clear your app's data in between runs.
    adb shell 'CLASSPATH=$(pm path androidx.test.services) app_process / \
      androidx.test.services.shellexecutor.ShellMain am instrument -w -e \
      targetInstrumentation com.example.test/androidx.test.runner.AndroidJUnitRunner \
      androidx.test.orchestrator/.AndroidXTestOrchestrator'
    

Como mostra a sintaxe do comando, instale o Android Test Orchestrator e use-o diretamente.

Observação: se você não sabe qual é sua instrumentação de destino, procure-a executando este comando:

    adb shell pm list instrumentation

Arquitetura

O APK de serviço do Orchestrator é armazenado em um processo separado do APK de teste e do APK do app em teste, como mostra a Figura 1:

Figura 1. Estrutura do APK do Android Test Orchestrator.

O Android Test Orchestrator coleta testes do JUnit no início da execução do conjunto de testes, mas depois os executa separadamente, na própria instância de Instrumentation.

Acessar o contexto do app

Para acessar o contexto do app em teste, chame o método estático ApplicationProvider.getApplicationContext(). Se você criou uma subclasse personalizada de Application no app, esse método retorna o contexto da subclasse personalizada.

Se você implementa ferramentas, pode acessar APIs de teste de nível baixo usando a classe InstrumentationRegistry. Essa classe inclui o objeto Instrumentation, o objeto Context do app de destino, o objeto Context do app de teste e os argumentos da linha de comando passados para seu teste. Esses dados são úteis quando você programa testes usando o framework UI Automator ou quando seus testes dependem do contexto do app.

Filtrar testes

Nos testes JUnit 4.x, é possível usar anotações para configurar a execução dos testes. Esse recurso minimiza a necessidade de adicionar código clichê e condicional nos testes. Além das anotações padrão compatíveis com o JUnit 4, o executor de testes também é compatível com anotações específicas do Android, entre elas:

  • @RequiresDevice: especifica que o teste deve ser executado apenas em dispositivos físicos, não em emuladores.
  • @SdkSuppress: suprime a execução do teste em uma API do Android de nível inferior ao especificado. Por exemplo, para suprimir a execução de testes em todos os níveis de API inferiores ao 23, use a anotação @SDKSuppress(minSdkVersion=23).
  • @SmallTest, @MediumTest e @LargeTest: classificam o tempo que um teste deve levar para ser executado e, consequentemente, com que frequência é possível executá-lo.

Fragmentar testes

O executor de testes é compatível com a divisão de um único conjunto de testes em vários fragmentos. Assim, você terá facilidade para executar testes pertencentes ao mesmo fragmento como um grupo, sob a mesma instância de Instrumentation. Cada fragmento é identificado por um número de índice. Ao executar testes, use a opção -e numShards para especificar o número de fragmentos separados a serem criados, e a opção -e shardIndex para especificar qual fragmento será executado.

Por exemplo, para dividir o conjunto de testes em 10 fragmentos e executar apenas os testes agrupados no segundo fragmento, use o seguinte comando:

    adb shell am instrument -w -e numShards 10 -e shardIndex 2
    

Mais informações

Para saber mais sobre como usar esse executor de testes, consulte a Referência de API.

Para usar a classe AndroidJUnitRunner, inclua-a como um dos pacotes do projeto, conforme descrito em Configurar projetos para o AndroidX Test.

Outros recursos

Para saber mais sobre o uso do AndroidJUnitRunner, consulte os recursos a seguir.

Exemplos

  • AndroidJunitRunnerSample (em inglês): mostra anotações de teste, testes parametrizados e criação de conjunto de testes.