MVVM and DataBinding: Android Design Patterns
This article describes the MVVM Design Pattern and its components, data binding, and other design patterns and architectural concepts for the Android platform. By Matei Suica.
Sign up/Sign in
With a free Kodeco account you can download source code, track your progress, bookmark, personalise your learner profile and more!
Create accountAlready a member of Kodeco? Sign in
Contents
MVVM and DataBinding: Android Design Patterns
30 mins
- Getting Started
- Understanding Design Patterns
- Using Architectural Design Patterns
- Common Architectural Design Patterns in Android
- MVC and MVP
- Taking the Next Step: MVVM
- Understanding MVVM Components
- Defining the Role of the View
- Defining the Model
- Finding the ViewModel’s Place in MVVM
- Improving Testability
- Hiding Behind Interfaces and Dependency Injection
- Testing Each Component
- Best practices in Testing MVVM
- Adding Android’s Architecture Components
- Using DataBinding
- Adding Android’s own ViewModel
- Loose Coupling with LiveData
- The Database in the Room
- Searching For More
- Clean Architecture
This article describes the theory behind the Model–View–ViewModel (MVVM) design pattern and its components. If you want to experiment with it hands-on, open an old project with spaghetti code. If you don’t have one, you can get one from GitHub. Then, try to use the MVVM components introduced in this article.
In some ways, software development hasn’t changed much in the last decade. The basic challenges remain the same:
- Writing clean code.
- Having a flexible architecture.
- Testing the code.
- Creating a great user experience.
- Developing features faster than product management can think of them. :]
All these problems had a solution by the time Android entered the market. Desktop and web application developers already had a knowledge base for writing user interfaces. Those solutions worked for Android too, but they were far from ideal.
Android was initially based on Java and apps were typically implemented using MVC (Model View Controller). Ten years later, there’s Kotlin…and there’s MVVM. It was a long journey over those ten years, so let’s catch up!
Note: This article assumes you’re familiar with the basics of Android and Kotlin. If you’re new to Android Development, check out our Android and Kotlin for Beginners series. Need to catch up on Kotlin? Take a look at Kotlin For Android: An Introduction
Note: This article assumes you’re familiar with the basics of Android and Kotlin. If you’re new to Android Development, check out our Android and Kotlin for Beginners series. Need to catch up on Kotlin? Take a look at Kotlin For Android: An Introduction
Getting Started
Understanding Design Patterns
Design patterns represent reusable architectural building blocks within a program. Good building blocks in your code will:
- Lead to clean code.
- Resolve common problems using common paradigms, making it easier for multiple developers to work on the same project.
- Be robust and well tested.
- Be easier to understand than free-form code.
Imagine entering a bathroom. At a glance, you can identify a toilet. You know what it does and how to use it. You then recognize the sink. Hopefully, you don’t need to poke it and test what it does. The pattern of a bath tub is something you already know as well.
Not all sinks are the same. For example, in the UK, you might find a sink with separate pipes for cold water and hot water. While it’s unusual for the rest of the world, you’d still know how to use the sink.
With design patterns, developers can apply known solutions to existing problems.
Using Architectural Design Patterns
The concept of design patterns appeared in a famous book by the same name, which described three categories for these patterns:
- Creational
- Structural
- Behavioral
A fourth category, Architectural design patterns, helps developers follow an architectural style. They help you separate different components within a project.
In the Enterprise world, one of the most popular design patterns is the “three-tier” or “three layers” pattern. Another useful one is the “client-server” model. Mobile apps also benefit from many of these patterns, but some work better than others.
MVVM is an architectural design pattern that works well for mobile apps.
Common Architectural Design Patterns in Android
MVC and MVP
Model-View-Controller (MVC) and Model-View-Presenter (MVP) are two design patterns that are very similar and have much in common with MVVM. Google didn’t push for one single design pattern for Android in the beginning. However, the documentation uses MVC more often than not. This pattern has three components: Model, View, and Controller.
In MVC, communication between components looks like a triangle:
- The View displays the state of the Model,
- The Controller handles the View input.
- The Model stores the result that comes out of the Controller.
MVC can be hard to test because of this communication model. Navigating the code can also be tedious. The business logic should split between the Controller and the Model, but sometimes the logic leaks into the View.
This creates a kind of coupling that has a spiral effect. In the end, it encourages Android developers to put the bulk of the code in an Activity or Fragment class. The problem has a nickname: “massive view controller”. Ironically, this problem has the same initials as MVC. But it makes the app hard to maintain and nearly impossible to test.
Despite this, the pattern is still good enough for small projects. But there are better patterns available.
Note: Have you ever seen an Activity or a Fragment that exceeds 1000 lines of code? That’s a Massive View Controller! It’s that file that always generates merge conflicts. It has 0% test-coverage, and everyone avoids changing it.
Note: Have you ever seen an Activity or a Fragment that exceeds 1000 lines of code? That’s a Massive View Controller! It’s that file that always generates merge conflicts. It has 0% test-coverage, and everyone avoids changing it.
For example, MVP shifts the “controller” in MVC between the Model and the View, naming it a Presenter. This helps concentrate the business logic in the Presenter. On the flip side, the Presenter is also responsible for adapting the data in the model for display in the View. For this reason, the Presenter is sometimes called a “supervising controller”.
The difference between MVC and MVP is not huge, but decoupling the Model from the View has advantages. It allows for more flexibility and offers easier UI and Unit Testing.
The problem is that the Presenter is still coupled with both the Model and the View. Time to take another step down the decoupling road!
Taking the Next Step: MVVM
Compared to MVP, MVVM decouples the View from the ViewModel by using something called a Binder. The ViewModel doesn’t know about the View or Views subscribed for changes. The Binder delivers the changes from the ViewModel to the View. This allows developing and testing the View in isolation without breaking the ViewModel.
Think about it: should your UI influence the business logic? You’re right, it shouldn’t!
This pattern isn’t perfect either, but it’s very good. So, let’s dig into it.