Unit & Automation Testing in Android - Stanislav Gatsev, Melon


Published on

  • Be the first to comment

No Downloads
Total views
On SlideShare
From Embeds
Number of Embeds
Embeds 0
No embeds

No notes for slide

Unit & Automation Testing in Android - Stanislav Gatsev, Melon

  1. 1. Unit and Automation Testing on Android Stanislav Gatsev Android Team Lead, Melon Inc.
  2. 2. Who am I? Stanislav Gatsev Android Team Lead +359 89 891 4481 stanislav.gatsev@melontech.com http://www.melon.bg
  3. 3. What is Android? o World's most popular mobile platform o Every day another million users power up their Android devices for the first time o Using Android SDK we can develop software for almost everything from smartphones and tablets to glasses, watches, TVs and even cars.
  4. 4. Why we automate testing? o We save time !!! o We improve our code quality o We support live documentation o We run our regression tests o We fight fragmentation
  5. 5. Our Example Project
  6. 6. What Can We Test? o We can test our logic, algorithms, calculations o We can test our UI and navigation logic o We can test IO operations, database and network operations o And more... @SmallTest public void test_addOperatorInJava() throws Exception { Assert.assertEquals(4, 2 + 2); Assert.assertEquals(27, 25 + 2); } @SmallTest public void test_FieldsAreVisible() { ViewAsserts.assertOnScreen(mRootView, mEmailEditText); ViewAsserts.assertOnScreen(mRootView, mPasswordEditText); ViewAsserts.assertOnScreen(mRootView, mLoginActionLayout); }
  7. 7. How we automate testing? o We use JUnit o We mock our objects o We are using activity testing framework o We click with Robotium
  8. 8. JUnit and Android We can use the JUnit TestCase class to do unit testing on a class that doesn't call Android APIs. TestCase is also the base class for AndroidTestCase, which we can use to test Android-dependent objects. Besides providing the JUnit framework, AndroidTestCase offers Android-specific setup, teardown, and helper methods. public class UtilTests extends AndroidTestCase { @SmallTest public void test_StringToLatLngValidValues() throws Exception { String latLngString = "34.009555,-118.497072"; LatLng latLng = Util.stringToLatLng(latLngString); Assert.assertEquals(Double.compare(latLng.latitude, 34.009555), 0); Assert.assertEquals(Double.compare(latLng.longitude, -118.497072), 0); } @SmallTest public void test_StringToLatLngValidInvalues() throws Exception { String latLngString = "34.009555,-a118.497072"; LatLng latLng = Util.stringToLatLng(latLngString); Assert.assertEquals(Double.compare(latLng.latitude, 0), 0); Assert.assertEquals(Double.compare(latLng.longitude, 0), 0); } }
  9. 9. Why we use Mocks? The objective of unit testing is to exercise just one method at a time, but what happens when that method depends on other things—hard-to-control things such as the network, or a database. The solution is the Mock object. It is simply a debug replacement for a real- world object.
  10. 10. Mockito Mockito is the way we mock objects in Android. As its developers say: “Mockito is a mocking framework that tastes really good. It lets you write beautiful tests with clean & simple API. Mockito doesn't give you hangover because the tests are very readable and they produce clean verification errors.” • https://code.google.com/p/dexmaker/ • System property hack
  11. 11. Mockito and Android //create Mock of server communication final WeatherServerRequest weatherServerRequest = Mockito.mock(WeatherServerRequest.class); //stub the actual network call and return empty object ServerResponse serverResponse = new ServerResponse(); Mockito.when(weatherServerRequest.getResponse()).thenReturn(serverResponse); //create mock of the refresh-able and the observers subject IRefreshable refreshable = Mockito.mock(IRefreshable.class); ISubject subject = Mockito.mock(ISubject.class); runWeatherWorkerThread(refreshable, subject, weatherServerRequest); //verify if refresh-able start callback is called Mockito.verify(refreshable).onStartRefresh(); //verify if the observers callback is called Mockito.verify(subject).updateData(Mockito.anyMapOf(String.class, ServerResponse.class)); //verify if refresh-able end callback is called Mockito.verify(refreshable).onEndRefresh(); =+
  12. 12. Activity tests ActivityInstrumentationTestCase2 This is the class which helps us test our Activities. It has direct reference to the tested activity and you have the ability to run whole test or just parts of it in the UI Thread. @SmallTest public void test_viewPagerHasAllLocations() throws Throwable { //Creates the data fetcher mock and injects it to the Activity for every test createDataFetcherMock(); runTestOnUiThread(new Runnable() { @Override public void run() { //reinitialize activity with new data fetcher getActivity().init(); } }); //asserts if the view pager has the same number of items the data fetcher returned Assert.assertEquals(3, mViewPager.getAdapter().getCount()); }
  13. 13. Robotium o It is a lot easier to write our automation tests o Helpful API for executing user actions o Flexible results assertion o Hybrid apps are supported o We can use it in our Activity tests
  14. 14. Robotium in action @LargeTest public void test_addNewLocation() throws Throwable { getInstrumentation().waitForIdleSync(); moveMapToPosition(); getInstrumentation().waitForIdleSync(); //gets the root view of the Activity View rootView = getActivity().findViewById(android.R.id.content); //long click in the center of the screen mSolo.clickLongOnScreen(rootView.getWidth()/2, rootView.getHeight()/2); getInstrumentation().waitForIdleSync(); //get first weather location WeatherDataFetcher dataFetcher = getActivity().getDataFetcher(); List<WeatherLocation> weatherLocations = dataFetcher.getLocationsList(); Assert.assertEquals(1, weatherLocations.size()); //check if the location is the right one WeatherLocation weatherLocation = weatherLocations.get(0); Assert.assertEquals("Santa Monica, CA", weatherLocation.getLocationName()); //clears DB dataFetcher.removeLocation(0); }
  15. 15. Thank you! Questions?
  16. 16. References o https://developer.android.com o https://code.google.com/p/robotium/ o https://github.com/mockito/mockito o http://blog.gfader.com/2010/10/why-are-automated-tests-so-important.html o http://media.pragprog.com/titles/utj/mockobjects.pdf o http://www.embedded.com/design/prototyping-and- development/4398723/The-mock-object-approach-to-test-driven- development