Espresso-Web é um ponto de entrada para trabalhar com componentes de IU do Android WebView. O Espresso-Web reutiliza Atoms da conhecida API WebDriver (em inglês) para examinar e controlar o comportamento de um WebView.
Quando usar o Espresso-Web
Use o Espresso-Web para testar seus aplicativos híbridos, especialmente a integração dos seus
os componentes da interface nativa do app com os WebView
componentes de IU. É possível usar a API do Espresso-Web com outras
APIs do Espresso para interagir completamente com elementos da Web em objetos WebView
.
Se você precisar testar apenas o WebView
, e não o
interações entre WebView
e componentes nativos no seu app, considere
criar um teste geral da Web usando um framework como o WebDriver. Se você usa um framework de teste da Web,
usar um dispositivo Android ou uma máquina virtual Java, o que facilita os testes
para que sejam executados
com mais rapidez e confiança. Com isso em mente, o Espresso-Web permite reutilizar
seus átomos personalizados do WebDriver, o que proporciona muita flexibilidade,
ao escrever testes que você planeja executar em aplicativos da Web autônomos e
apps que incluem uma interface do Android.
Como funciona
Da mesma forma que o onData()
do Espresso
uma interação WebView
compreende vários Atoms.
As interações WebView
usam uma combinação da linguagem de programação Java e uma
JavaScript para fazer seu trabalho. Como não há chance de introduzir
condições de corrida ao expor dados do ambiente JavaScript,
O Espresso vê no lado baseado em Java uma cópia isolada que retorna dados do
Web.WebInteraction
é totalmente compatível, o que permite verificar todos os dados retornados de
uma solicitação.
O que é um Atom do WebDriver?
O framework do WebDriver usa Atoms para localizar e manipular elementos da Web
programaticamente. Os Atoms são usados pelo WebDriver para permitir a manipulação do navegador. Um
Conceitualmente, o Atom é semelhante a um
O ViewAction
, uma plataforma
que executa uma ação na interface. Você expõe Atoms usando uma lista de
métodos definidos, como findElement()
e getElement()
, para direcionar o
do navegador do ponto de vista do usuário. No entanto, se você usar o WebDriver
diretamente o framework, os Atoms precisam ser devidamente orquestrados, exigindo lógica que
é bem prolixo.
No Espresso, as classes Web
e Web.WebInteraction
unir esse código clichê e proporcionar uma experiência semelhante à do Expresso para interagir com a WebView.
objetos. Portanto, no contexto de uma WebView
, os Atoms são usados como
Uma substituição para as ViewMatchers
e ViewActions
do Espresso.
A API é bastante simples:
onWebView()
.withElement(Atom)
.perform(Atom)
.check(WebAssertion)
onWebView()
.withElement(Atom)
.perform(Atom)
.check(WebAssertion);
Para saber mais, leia a documentação do Selenium sobre Atoms (em inglês).
Implementar o WebView
Siga as orientações mostradas nas seções a seguir para trabalhar
WebView
nos testes do app.
Pacotes
Para incluir o Espresso-Web no projeto, siga estas etapas:
- Abra o arquivo
build.gradle
do seu app. Geralmente, não é a no arquivobuild.gradle
de nível superior,app/build.gradle
. Adicione a seguinte linha nas dependências:
O Espresso-Web é compatível somente com o Espresso 2.2 ou posterior e para a versão 0.3 ou superior da biblioteca de teste. com as seguintes linhas:
androidTestImplementation 'androidx.test:runner:1.6.1'
androidTestImplementation 'androidx.test:rules:1.6.1'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.6.1'
androidTestImplementation('androidx.test:runner:1.6.1')
androidTestImplementation('androidx.test:rules:1.6.1')
androidTestImplementation('androidx.test.espresso:espresso-core:3.6.1')
Uso comum da API
O onWebView()
é o principal ponto de entrada ao trabalhar com a WebView no Android usando
Use esse método para realizar testes do Espresso-Web, como o
seguintes:
onWebView()
.withElement(findElement(Locator.ID, "link_2")) // similar to onView(withId(...))
.perform(webClick()) // Similar to perform(click())
// Similar to check(matches(...))
.check(webMatches(getCurrentUrl(), containsString("navigation_2.html")))
onWebView()
.withElement(findElement(Locator.ID, "link_2")) // similar to onView(withId(...))
.perform(webClick()) // Similar to perform(click())
// Similar to check(matches(...))
.check(webMatches(getCurrentUrl(), containsString("navigation_2.html")));
Neste exemplo, o Espresso-Web localiza um elemento DOM com ID "link_2"
e
clicar nela. A ferramenta verifica se o WebView envia uma solicitação GET
que contém a string "navigation_2.html"
.
Compatibilidade com JavaScript
Ao executar seus testes, o sistema realiza todas as interações do WebView usando JavaScript. Portanto, para oferecer suporte à avaliação do JavaScript, o WebView em teste o JavaScript precisa estar ativado.
É possível forçar a ativação do JavaScript chamando
forceJavascriptEnabled()
como uma ação em sua atividade em
teste, conforme mostrado no
snippet de código a seguir.
@RunWith(AndroidJUnit4::class)
class MyTestSuite {
@get:Rule val activityScenarioRule =
activityScenarioRule<MyWebViewActivity>()
@Test fun testWebViewInteraction() {
onWebView().forceJavascriptEnabled()
}
}
Interações comuns na Web
As interações comuns com objetos Web.WebInteraction
incluem o seguinte:
-
withElement()
faz referência a um elemento DOM na WebView.Exemplo:
-
withContextualElement()
faz referência a um elemento DOM com escopo na WebView, em relação a outro elemento DOM. Você deve chamarwithElement()
primeiro para estabelecer a referênciaWeb.WebInteraction
(elemento DOM).Exemplo:
-
check()
avalia uma condição para garantir que ela seja resolvida paratrue
.Exemplo:
onWebView()
.withElement(findElement(Locator.ID, "teacher"))
.withContextualElement(findElement(Locator.ID, "person_name"))
.check(webMatches(getText(), containsString("Socrates")))onWebView()
.withElement(findElement(Locator.ID, "teacher"))
.withContextualElement(findElement(Locator.ID, "person_name"))
.check(webMatches(getText(), containsString("Socrates"))); -
O
perform()
executa uma ação dentro de um WebView, como clicando em um elemento.Exemplo:
-
reset()
reverte o WebView ao estado inicial. Isso é necessário quando uma uma ação, como um clique, introduz uma mudança na navegação que facilita Objetos ElementReference e WindowReference inacessíveis.Observação:embora o uso de
reset()
seja útil quando fazer declarações em relação a fluxos de trabalho de várias páginas, como envios de formulário, Em geral, os testes precisam ter escopo limitado e foco em uma única página.Exemplo:
Exemplo
O exemplo a seguir testa se, depois de inserir texto em um WebView, selecionando um botão Enviar, o mesmo texto aparecerá em um elemento diferente no a mesma WebView:
const val MACCHIATO = "Macchiato"
@RunWith(AndroidJUnit4::class)
class MyEspressoWebTestSuite {
@Test fun typeTextInInput_clickButton_SubmitsForm() {
// Create an intent that displays a web form.
val webFormIntent = Intent()
// ...
// Lazily launch the Activity with a custom start Intent per test.
ActivityScenario.launchActivity(webFormIntent)
// Selects the WebView in your layout. If you have multiple WebView
// objects, you can also use a matcher to select a given WebView,
// onWebView(withId(R.id.web_view)).
onWebView()
// Find the input element by ID.
.withElement(findElement(Locator.ID, "text_input"))
// Clear previous input and enter new text into the input element.
.perform(clearElement())
.perform(DriverAtoms.webKeys(MACCHIATO))
// Find the "Submit" button and simulate a click using JavaScript.
.withElement(findElement(Locator.ID, "submitBtn"))
.perform(webClick())
// Find the response element by ID, and verify that it contains the
// entered text.
.withElement(findElement(Locator.ID, "response"))
.check(webMatches(getText(), containsString(MACCHIATO)))
}
}
public static final String MACCHIATO = "Macchiato";
@Test
public void typeTextInInput_clickButton_SubmitsForm() {
// Create an intent that displays a web form.
Intent webFormIntent = new Intent();
// ...
// Lazily launch the Activity with a custom start Intent per test.
ActivityScenario.launchActivity(webFormIntent);
// Selects the WebView in your layout. If you have multiple WebView objects,
// you can also use a matcher to select a given WebView,
// onWebView(withId(R.id.web_view)).
onWebView()
// Find the input element by ID.
.withElement(findElement(Locator.ID, "text_input"))
// Clear previous input and enter new text into the input element.
.perform(clearElement())
.perform(DriverAtoms.webKeys(MACCHIATO))
// Find the "Submit" button and simulate a click using JavaScript.
.withElement(findElement(Locator.ID, "submitBtn"))
.perform(webClick())
// Find the response element by ID, and verify that it contains the
// entered text.
.withElement(findElement(Locator.ID, "response"))
.check(webMatches(getText(), containsString(MACCHIATO)));
}
Outros recursos
Para mais informações sobre o uso do Espresso-Web em testes do Android, consulte a recursos a seguir.
Amostras
- WebBasicSample (em inglês):
Usar o Espresso-Web para interagir com objetos
WebView
.