Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
Acceptance test like a pro
Search
Sponsored
·
Ship Features Fearlessly
Turn features on and off without deploys. Used by thousands of Ruby developers.
→
Rodrigo Sicarelli
May 07, 2016
Technology
200
2
Share
Acceptance test like a pro
Tirando vantagem do Espresso e Android Studio para criar testes de aceitação incríveis
Rodrigo Sicarelli
May 07, 2016
More Decks by Rodrigo Sicarelli
See All by Rodrigo Sicarelli
Melhores práticas para encontrar Crashes utilizando o CrashLytics
rsicarelli
2
170
Firebase para Desenvolvedores
rsicarelli
4
190
A importância de ter Lazy Clients - TDC 2016
rsicarelli
3
230
Erlang - Why?
rsicarelli
0
75
Android Support Library v23.2.0
rsicarelli
0
60
ProGuard - O que é e porque utilizar
rsicarelli
0
140
Other Decks in Technology
See All in Technology
Gaussian Splattingの実用化 - 映像制作への展開
gpuunite_official
0
200
インプロセスQAのための要因から捉えるプロジェクトリスクマネジメントnano #1 開発リソース効率状態への対処 #jasstnano
barus_qa
0
210
AWSアップデートから考える継続的な運用改善
toru_kubota
2
310
ECSのTerraformモジュールにコントリビュートした話
harukasakihara
0
250
Claude Code / Codex / Kiro に AWS 権限を 渡すとき、何を設計すべきか
k_adachi_01
6
1.9k
最新技術を"今は選ばない"という技術選定
leveragestech
PRO
0
320
20260515 OpenIDファウンデーション・ジャパンご紹介
oidfj
0
250
AWS WAFの運用を地道に改善し、自社で運用可能にするプラクティス
andpad
1
610
freeeで運用しているAIQAについて
qatonchan
1
660
PdM・Eng・QAで進めるAI駆動開発の現在地/aidd-with-pdm-eng-qa
shota_kusaba
0
260
サイボウズ、プラットフォームエンジニアリング始めるってよ ― プラットフォームチームの事業貢献と組織アラインメントの強化
ueokande
0
120
生成AI時代に信頼性をどう保ち続けるか - Policy as Code の実践
akitok_
1
510
Featured
See All Featured
WCS-LA-2024
lcolladotor
0
590
State of Search Keynote: SEO is Dead Long Live SEO
ryanjones
0
190
From Legacy to Launchpad: Building Startup-Ready Communities
dugsong
0
210
HTML-Aware ERB: The Path to Reactive Rendering @ RubyCon 2026, Rimini, Italy
marcoroth
1
59
How People are Using Generative and Agentic AI to Supercharge Their Products, Projects, Services and Value Streams Today
helenjbeal
1
180
Java REST API Framework Comparison - PWX 2021
mraible
34
9.3k
<Decoding/> the Language of Devs - We Love SEO 2024
nikkihalliwell
1
210
Hiding What from Whom? A Critical Review of the History of Programming languages for Music
tomoyanonymous
2
810
Thoughts on Productivity
jonyablonski
76
5.2k
Why Our Code Smells
bkeepers
PRO
340
58k
The Curious Case for Waylosing
cassininazir
1
350
The World Runs on Bad Software
bkeepers
PRO
72
12k
Transcript
Rodrigo Sicarelli Acceptance test like a pro Tirando vantagem do
Espresso
Android Dev BR medium.com/android-dev-br androiddevbr.org +1100 membros Novo artigo toda
semana Newsletter semanal Canal direto com GDE’s Codehelp, feedbacks, learn etc etc etc
OpenMovie github.com/rsicarelli/openmovie
Acceptance tests
Acceptance tests
The sad truth
May the user be with you
Hermetic testing testdroid.com/tech/strive-for-hermetic-but-never-compromise-integrity-of-app
Hermetic testing
Hermetic testing semaphoreci.com/community/tutorials/how-to-deal-with-and-eliminate-flaky-tests
External dependencies Your code
Isolate all the external dependencies Your code
Create an fake environment!
Product flavors developer.android.com/intl/pt-br/tools/building/configuring-gradle
The “mock" flavor debug release prod mock android-developers.blogspot.com.br/2015/12/leveraging-product-flavors-in-android
The “mock" flavor codelabs.developers.google.com/codelabs/android-testing
Which one should I use? View Network
Which one should I use? View Network Injection medium.com/@patrykpoborca/making-a-best-practice-app-4-dagger-2-267ec5f6c89a#.iwom3rir5
Which one should I use? google.github.io/dagger blog.sqisland.com/2016/01/daggerless-di-testing
MovieClient @Override public void findMoviesByQuery(String query, Callback callback) {} @Override
public void findMovieById(String id, Callback callback) {}
ClientModule @Module public class ClientModule { @Provides public MovieClient provideMovieClient()
{ return new MovieClient(); } }
Our Presenter public class Presenter { @Inject MovieClient client; }
Structure
Our prod flavor @Override public void findMoviesByQuery(String query, Callback callback)
{ //Calling the API; } @Override public void findMovieById(String id, Callback callback) { //Calling the API; }
Our mock flavor @Override public void findMoviesByQuery(String query, Callback callback)
{ //Return a fake json; } @Override public void findMovieById(String id, Callback callback) { //Return a fake json; }
Isolate all the external dependencies Your code
Not today, son.
Login screen play.google.com/store/apps/details?id=br.com.elo7.appbuyer
Login screen Is the Activity open? Can I perform some
click? etc etc etc
In Espresso we trust developer.android.com/intl/pt-br/reference/android/app/Instrumentation
My activity is open? waitForActivity() and waitForActivityWithTimeout() developer.android.com/intl/pt-br/reference/android/app/Instrumentation.ActivityMonitor
Using the ActivityMonitor public void registerMonitor(Class<? extends Activity> activityClass) {
if (monitor != null) { getInstrumentation().removeMonitor(monitor); } monitor = new Instrumentation.ActivityMonitor(activityClass.getName(), null, false); getInstrumentation().addMonitor(monitor); } @Test public void shouldTestSomething() { onView(withId(R.id.login)).perform(click()); monitor.waitForActivity(); onData(anything()) .inAdapterView(withId(R.id.product_grid_view)) .atPosition(0) .perform(click()); } public class BaseActivityTestCase extends ActivityTestCase {...}
Using the Monitor @Test public void shouldTestSomething() { onView(withId(R.id.login)).perform(click()); monitor.waitForActivity();
registerMonitor(OtherActivity.class); onData(anything()) .inAdapterView(withId(R.id.product_grid_view)) .atPosition(0) .perform(click()); monitor.waitForActivity();//new monitor! }
Searching while typing
In Espresso we trust! developer.android.com/intl/pt-br/reference/android/support/test/espresso/IdlingResource
Usage public final class SimpleCountingIdlingResource implements IdlingResource {…} public class
EspressoIdlingResource { ... public static void busy() { simpleCountingIdlingResource.increment(); } public static void idle() { simpleCountingIdlingResource.decrement(); } ... }
Usage @Override public void findMoviesByQuery(String query, Callback callback) { EspressoIdlingResource.busy();
... searchResponseCall.enqueue(... { @Override public void onResponse(...) { EspressoIdlingResource.idle(); } @Override public void onFailure(...) { EspressoIdlingResource.idle(); } }); }
Usage @Before private void registerIdlingResource() { Espresso.registerIdlingResources( rule.getActivity().getCountingIdlingResource()); } @After
public void unregisterIdlingResource() { Espresso.unregisterIdlingResources( rule.getActivity().getCountingIdlingResource()); }
Oh yeah
Next steps Inject modules inside the tests Remove test code
Acceptance test like a pro Tirando vantagem do Espresso +RodrigoSicarelli2
[email protected]
github.com/rsicarelli/openmovie androiddevbr.org