Deep integration of Realm in Android production code, Part-2, with MVP

Viraj Tank
4 min readJul 9, 2016

--

As we discussed safe integration of Realm earlier in part-1,

In this part-2 we will cover,

  • Auto update feature of Realm & Deep integration
  • Steps to follow, when doing deep integration of Realm in production code, in combination with MVP(Model View Presenter) design pattern, Dagger, Rx-Java, Retrofit & Annotations.

Auto update feature of Realm & Deep integration

  • What is Auto-Update feature of Realm?

In Realm all RealmObjects and RealmResults are LIVE objects which means until we close the Realm instance, we keep getting a callback if the queried data is modified.

Let’s say we have a view with list of data, if user makes changes on those data in some other view, usually we have to manually update the view with list, with Realm’s Auto-update feature we will get a callback and we can easily update the view without any boilerplate code.

  • Deep Integration

Deep integration is where we heavily depend on Realm and use all of Realm’s features. This approach is useful if we are creating a new codebase or if we are willing to do heavy refactoring on our production code.

Advantages

  • We will be able to use Auto-update feature of Realm, which is a big plus
  • Less boilerplate code
  • All the queries we make are much faster than safe integration because we don’t make a copy
  • All Realm queries needs less memory because of zero copy object store idea of Realm

Disadvantages

  • We create heavy dependency on Realm
  • We have to do major refactoring on production code, which will involve, DAO, presenter and data layer.
  • We have to pay extra attention to thread management

Steps for Safe Integration

Step for safe integration can be found in part-1 of the post

Steps for Deep Integration

1. (Json+View)Model to (Json+View+Realm)Model

We will extend RealmObject in our json+view Model, that will allow us to use same model class for json parsing, view building and Realm operations.

A sample model looks like this,

2. Presenter + Realm

Now that our model class is RealmObject, we can not pass it across threads, Also to keep Realm’s impact on our production code as low as possible, we will keep all Realm operations within respective Presenter. This means that our presenter will also take responsibilities of being a data source.

Bind + Unbind

As a first step we need a Realm instance for each presenter. We can get a fresh copy of Realm when we bind the view to presenter and close the Realm instance when we unbind the view from presenter.

A sample bind and unbind method of presenter looks like this,

Auto updating the view when Model data updates

In Realm, RealmObjects and RealmResults are LIVE objects, which means that once we query, we can listen for any further modification on the queried data.

To achieve this feature, we need to first setup a listener on queried data. There are two ways to do this,

  • Observable way
  • addChangeListener way

Read operations on MainThread() with Async()

Now that we have a single instance of Realm for entire presenter, we can only use that instance on mainThread of Android, which is pretty bad.

Realm provides a good solution for this problem, in form of Async() methods. We will do all Realm read operations on mainThread but we will use Realm’s Async methods to do all heavy operations on background thread.

Updating Realm models

Now that we have setup our Read query, whenever we make modification on any of the queried data, we will get a callback and we can easily update the view. We will not have to transfer the updated model across methods.

Lets have a look at Write to Realm method. Whenever we need fresh data from Network, we get the values and updated them on Realm, internally Realm will send a callback to our Read operation and we can update the view.

This is how a sample looks like,

Write operations + Threads

There are 2 ways we can handle write operations,

  • We can use the realm instance, we created in mainThread() and use executeTransactionAsync()
  • We can get a new Realm instance, perform write operation with executeTransaction() and close Realm instance

Both are safe ways to perform write operations and we will get the callback to read queries in both the cases.

Summary

TL;DR Deep integration of Realm brings many exciting features, but we have to be careful on thread handling.

Complete source code

Complete source code is available on GitHub.

--

--