DZone
Thanks for visiting DZone today,
Edit Profile
  • Manage Email Subscriptions
  • How to Post to DZone
  • Article Submission Guidelines
Sign Out View Profile
  • Post an Article
  • Manage My Drafts
Over 2 million developers have joined DZone.
Log In / Join
Refcards Trend Reports
Events Video Library
Refcards
Trend Reports

Events

View Events Video Library

Zones

Culture and Methodologies Agile Career Development Methodologies Team Management
Data Engineering AI/ML Big Data Data Databases IoT
Software Design and Architecture Cloud Architecture Containers Integration Microservices Performance Security
Coding Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks
Culture and Methodologies
Agile Career Development Methodologies Team Management
Data Engineering
AI/ML Big Data Data Databases IoT
Software Design and Architecture
Cloud Architecture Containers Integration Microservices Performance Security
Coding
Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance
Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks

Last call! Secure your stack and shape the future! Help dev teams across the globe navigate their software supply chain security challenges.

Modernize your data layer. Learn how to design cloud-native database architectures to meet the evolving demands of AI and GenAI workloads.

Releasing software shouldn't be stressful or risky. Learn how to leverage progressive delivery techniques to ensure safer deployments.

Avoid machine learning mistakes and boost model performance! Discover key ML patterns, anti-patterns, data strategies, and more.

Related

  • Beginners Guide to Mocking in Scala
  • IntelliJ Integration for Mockito
  • TDD Typescript NestJS API Layers with Jest Part 1: Controller Unit Test
  • Unit Testing Static Methods With Mockito

Trending

  • Unlocking AI Coding Assistants Part 3: Generating Diagrams, Open API Specs, And Test Data
  • Integrating Security as Code: A Necessity for DevSecOps
  • Unlocking the Potential of Apache Iceberg: A Comprehensive Analysis
  • Beyond ChatGPT, AI Reasoning 2.0: Engineering AI Models With Human-Like Reasoning
  1. DZone
  2. Testing, Deployment, and Maintenance
  3. Testing, Tools, and Frameworks
  4. How to Use Mockito in Android

How to Use Mockito in Android

Learn how to integrate Mockito with your app and use the mock and spy methods to unit test your Android application.

By 
Lipika Gupta user avatar
Lipika Gupta
·
Apr. 28, 18 · Tutorial
Likes (5)
Comment
Save
Tweet
Share
51.4K Views

Join the DZone community and get the full member experience.

Join For Free

Unit testing is an important part of any product development lifecycle. The main purpose of unit testing is to test components in isolation from each other and that is how our code should be written as well. To achieve this task of writing test cases for a class in isolation from the others, there are times when we need to mock some objects or data while writing our JUnit test cases. As the name Mockito suggests, it is a framework that allows us to do just that.

If the UI related part of our code is already tested by some testing framework like Espresso, then it need not be tested again. Also, we do not need to test code that relies on the Android OS. So, we can use Mockito to test our non-UI or functional code that is not dependent on the Android OS.

Image title

By default, when we run our local unit test cases, they run against a modified version of the android.jar file which does not contain any actual code because of which, when we try to invoke any method of an Android class from our test case, we get an exception. This is done to ensure that we test only our code and do not depend on some default behavior of the Android classes. We can also change this default behavior of throwing an exception to return zero or null values. However, we should avoid this as it could cause regressions in our test cases which are hard to debug. If we still wish to do this, it can be done by including the following in our project’s top-level build.gradle file:

android {
  ...
  testOptions {
    unitTests.returnDefaultValues = true
  }
}

We can substitute Android dependencies with mock objects. We can use Mockito for this to configure our mock objects to return some specific value when they are invoked.

Mockito Integration

To integrate Mockito in our Android apps, we first need to include the following dependencies in our app level build.gradle file.

dependencies {
    testCompile 'junit:junit:4.12'
    testCompile 'org.mockito:mockito-core:1.10.19'
}


Once we have added the required dependencies, we will create our test class in the directory module-name/src/test/java/, and add the @RunWith(MockitoJUnitRunner.class) annotation at the beginning of this class. This annotation tells the Mockito test runner to validate if the usage of the framework is correct and it also simplifies the mock object initializations.

We have to add @Mock annotation before the field declaration of any object we want to mock.

We can use the when() and thenReturn() methods to return a value when a particular condition is met in order to stub the behavior of any dependency.

Now, let’s have a look at a sample test class. The sample below checks that the method getHelloWorldString() of the class ClassUnderTest matches a given string.

public class ClassUnderTest {

    Context mContext;

    public ClassUnderTest(Context context) {
        mContext = context;
    }

    public String getHelloWorldString() {
        return mContext.getString(R.string.text_hello_word);
    }
}


public class ExampleUnitTest {

    private static final String TEST_STRING = "HELLO WORLD!";

    //As we don't have access to Context in our JUnit test classes, we need to mock it
    @Mock
    Context mMockContext;

    @Test
    public void readStringFromContext() {

        //Returns the TEST_STRING when getString(R.string.hello_world) is called
        when(mMockContext.getString(R.string.text_hello_word)).thenReturn(TEST_STRING);

        //Creates an object of the ClassUnderTest with the mock context
        ClassUnderTest objectUnderTest = new ClassUnderTest(mMockContext);

        //Stores the return value of getHelloWorldString() in result
        String result = objectUnderTest.getHelloWorldString();

        //Asserts that result is the value of TEST_STRING
        assertThat(result, is(TEST_STRING));
    }
}


How to Mock

We have two methods, mock() and spy(), that can be used to create mock methods or fields.

Using the mock() method, we create complete mock or fake objects. The default behavior of mock methods is to do nothing.

Using the spy() method, we just spy or stub specific methods of a real object. As we use real objects in this case, if we do not stub the method, then the actual method is called.

We generally use mock() when we need complete mock objects, and use spy() when we need partial mock objects for which we need to mock or stub only certain methods.

Let’s see how we can use mock() and spy() methods:

    @Test
    public void testMockMethod(){
        List mockList = Mockito.mock(ArrayList.class);
        mockList.add("hello world");
        Mockito.verify(mockList).add("hello world");
        assertEquals(0, mockList.size());
    }

    @Test
    public void testSpyMethod(){
        List spyList = Mockito.spy(new ArrayList());
        spyList.add("hello world");
        Mockito.verify(spyList).add("hello world");
        assertEquals(1, spyList.size());
    }


In the above example, when we add an object to a mocked list, the object isn't actually added as the actual add method is not called. However, when we call add on a spied list, the object is actually added as the actual method is called.

Mocking Behavior

Let’s look at how we can use Mockito methods to mock behavior of the mock or spy objects we create.

when() is used to configure simple return behavior for a mock or spy object.

doReturn() is used when we want to return a specific value when calling a method on a mock object. The mocked method is called in case of both mock and spy objects. doReturn() can also be used with methods that don’t return any value.

thenReturn is used when we want to return a specific value when calling a method on a mock object. The mocked method is called in case of mock objects, and real method in case of spy objects. thenReturn() always expects a return type.

To see a list of other available methods, you can refer to this link.

Now, let’s see how these methods can be used for unit testing:

    @Test
    public void testThenReturn(){
        //Create a mock object of the class Calculator
        Calculator mockCalculator = Mockito.mock(Calculator.class);

        //Return the value of 30 when the add method is called with the arguments 10 and 20
        Mockito.when(mockCalculator.add(10, 20)).thenReturn(30);

        //Asserts that the return value of add method with arguments 10 and 20 is 30
        assertEquals(mockCalculator.add(10, 20), 30);
    }

    @Test
    public void testDoReturn(){
        //Create a spy object of the class Calculator
        Calculator mockCalculator = Mockito.spy(new Calculator());

        //Return the value of 30 when the add method is called on the spied object with the arguments 10 and 20
        Mockito.doReturn(30).when(mockCalculator).add(10, 20);

        //Asserts that the return value of add method with arguments 10 and 20 is 30
        assertEquals(mockCalculator.add(10, 20), 30);
    }


Now, let’s look at the common assertions we can use to assert that some condition is true:

assertXYZ()
A set of assertion methods.

assertEquals(Object expectedValue, Object actualValue) 
Asserts that two objects are equal.

assertTrue(boolean condition)
Asserts that a condition is true.

assertFalse(boolean condition)
Asserts that a condition is false.

To see a list of all available assertions, you can refer to this link.

With the combination of the above methods and assertions, we can write test cases using the Mockito mocking framework.

Advantages & Disadvantages

Let’s have a look at the advantages and disadvantages of Mockito:

Advantages

  1. We can Mock any class or interface as per our need.
  2. It supports Test Spies, not just Mocks, thus it can be used for partial mocking as well.

Disadvantages

  1. Mockito cannot test static classes. So, if you’re using Mockito, it’s recommended to change static classes to Singletons.
  2. Mockito cannot be used to test a private method.

There are a few alternative mocking libraries like PowerMock, Robolectric, and EasyMock available as well which can be used.

This was all about how to write basic test cases using Mockito. I hope this blog encourages you to write unit test cases using Mockito or any similar framework. It might seem difficult at first, but once you get the hang of it, it will be of great use.

Mockito unit test Android (robot) Object (computer science)

Published at DZone with permission of Lipika Gupta. See the original article here.

Opinions expressed by DZone contributors are their own.

Related

  • Beginners Guide to Mocking in Scala
  • IntelliJ Integration for Mockito
  • TDD Typescript NestJS API Layers with Jest Part 1: Controller Unit Test
  • Unit Testing Static Methods With Mockito

Partner Resources

×

Comments

The likes didn't load as expected. Please refresh the page and try again.

ABOUT US

  • About DZone
  • Support and feedback
  • Community research
  • Sitemap

ADVERTISE

  • Advertise with DZone

CONTRIBUTE ON DZONE

  • Article Submission Guidelines
  • Become a Contributor
  • Core Program
  • Visit the Writers' Zone

LEGAL

  • Terms of Service
  • Privacy Policy

CONTACT US

  • 3343 Perimeter Hill Drive
  • Suite 100
  • Nashville, TN 37211
  • support@dzone.com

Let's be friends: