MVVM Architecture for Android consuming Marvel API: Dagger2, ViewModel, Room, LiveData, DataBinding, Retrofit, Repository Pattern. Part 1

Matteo Pasotti
5 min readSep 26, 2018

As Android Developer i always try to structure my projects in a proper way, following the common architectural principles like Separate of Concerns and Drive UI from a Model. In the last years Google has released the Android Architecture Components, a new collection of libraries that contains the lifecycle-aware components which help you design robust, testable, and maintainable apps.

This is the first article in a series of several in which i’m going to use MVVM (Model-View-ViewModel) pattern using Google’s new Lifecycle Architecture Components such as (LiveData, ViewModel, Room, DataBinding). For this purpose i’ve developed a sample Application in Kotlin where am consuming Marvel API (you need a key for them).

If you want to skip this part where i’ll talk about the basics, you can just check the second part here :

ComicsCatalog Sample App

This project is pretty simple, because we want to focus on how to use these components and how to structure our code in a right way. We’ll have a SplashScreen, a list of Characters and then a Detail screen.

Characters list

Once the app’s end user touch any of the list items, a details screen of the Character appears.

Character Detail screen

Interaction Diagram

The following diagram shows how components interact with each other to retrieve a list of Characters from Marvel Service or from our Database.

This architecture has mainly the following sections :

Model : It represents our data and business logic, exposed through observables. In my diagram this part consists of a Repository which is a source for data, thus whenever we need data, it always comes from a Repository. Our app should work offline too, for this purpose i’m using NetworkBoundResource which checks if we have local data and if yes we’ll use them, otherwise we’ll retrieve them from MarvelService.

View : Activity/Fragment. The role of this part is to observe (or subscribe to) a ViewModel observable to get data in order to update UI elements accordingly. We don’t want any logic here, but just retrieve data and then display them to the user.

ViewModel : This part interacts with data layer and prepares observables (LiveData or you can use RxJava) which can be observed by an Activity or a Fragment. It doesn’t depend by the View and should not be aware about the view who is interacting with.

Project setup

Let’s see now how to import and configure the main libraries and components that we’re going to use.

I’ve used Kotlin for this sample but am not going to explain how to configure it in your project. Just when you create a new project be sure to include Kotlin support.

The following picture shows some parts of my Gradle file for components like Dagger2 (Dependency Injection), Room (Database), ViewModel and LiveData :

Currently i’m using these versions :

ext.lifecycle_version = "1.1.1"
ext.room_version = "1.1.0"
ext.dagger_version = "2.13"

Configure the Database : Room and Entities

Like i’ve already said before this is the first article in a series of several where i’ll explain how to structure your projects using new architecture components released by Google. Let’s start then with the database, Room.

What we want is to retrieve Characters from a server and then store them inside our local database.

When using the Room persistence library, you define sets of related fields as entities. For each entity, a table is created within the associated Database object to hold the items. By default, Room creates a column for each field that’s defined in the entity.

Therefore we need an Entity class called Character which is what we want to store :

  • Room creates a table for each class annotated with Entity.
  • We can define primary keys using primaryKeys property or adding the @PrimaryKey annotation to the fields.
  • We can annotate with @Embedded the nested fields which they can be referenced directly in the SQL queries.

Once we have defined our Entities, we need to create DAOs (Data Access Objects) which are responsible for defining the methods that access the database. We define some main queries, annotated with @Query, which will be used in Repository class to update or retrieve data inside the database :

Last step, we have defined the Entity class Character and its corresponding methods but we’ve not yet created the database which brings all these pieces together. We define an abstract class which extends RoomDatabase, annotated with @Database. It defines the entities (our tables), the DAOs which access them, the number of version that needs to be incremented when the database schema is changed/altered.

These are the main parts about Room, in the next article i’ll try to explain how to structure our project using Dagger2.

This is my first article, if you enjoyed it, click on the applause button to help other people find it.

Feel free to get in touch with me on Linkedin.

--

--

Matteo Pasotti

Software Engineer @Spotify, Podcaster, Moving between countries