Architecture Components

Six months ago, my company wanted to be chosen as “Google Featured”.

So we needed to modify all of the UI/UX in the application that we’re currently serving. I happen to thought the previous application’s architecture was really messy. so I agreed with recreating project and started with a new project.

Unexpectedly, Google has released the Android Architecture Components at that time. So our team was adopted it and applied to a new product project. since released a new product project, I felt need to something clean up to architectures using android architecture components or trendy stacks. So I have clean up a new sample application.

This sample project is based on MVVM clean architecture.

kotlin based (almost 97%) with anko

Architecture Components (Lifecycle, LiveData, ViewModel, Room Persistence)

Material Design & Animations

Github API

DataBinding

Dagger2 for dependency injection

Retrofit2 & Gson for constructing the REST API

PreferenceRoom for efficient managing SharedPreferences

RecyclerViewPaginator for api paging

etc…

1. Configuring the ViewModel

what is ViewModel? ViewModel is one of the most important things on MVVM architecture. It makes loose coupling between activities and model’s business logic and also makes easier unit testing. Furthermore, it stores data for UI and it’s lifecycle-aware. Within use Dagger2, we can create it easier.

SearchActivityViewModel

This is sample codes of SearchActivity’s ViewModel. It used dependency Injection @inject with annotation, LiveData and repository patterns.

And next we should create a ViewModel in activity or fragment. but how should we do? ViewModelFactory makes it really easier. It create a new ViewModel and dagger will inject it to activity or fragment with lifecycle-aware. It’s a really wonderful harmony ViewModel and dagger.

And next, we can create the ViewModel just by three line with Dagger!

MainActivity

Inject instances using AndroidInjection.inject(this).

then viewModelFactory who annotated with @inject will be injected with Dagger. next, declare ViewModel using ViewModelProvider. Wow! we created a new ViewModel! How magical?

2. Configuring the Room Persistence

Room is one of the popular database library using SQLite made by Google.

IMO, Room has many advantages. It persists data over configuration changes, based on Objected-Oriented Modeling, supports migration, and it has really nice synergy with LiveData.

The Room persistence library provides an abstraction layer over SQLite to allow fluent database access while harnessing the full power of SQLite.

History Model

Firstly, we should create a model with @Entity annotation.

HistoryDao

And next, we should create DAO(Database Access Object) with @Dao annotation.

AppDatabase

Finally, create Database class extends RoomDatabase with @Database annotation. It’s all! and we can use it like below.

loadFromDb method

3. Configuring the Repository

Repository is one of the design pattern, defined by Eric Evens. It is one of the most useful and most widely applicable design patterns ever invented. Domain layer request needed data to repository, and repository tosses data from local repositories like database or SharedPreferences. It makes loose coupling between ViewModel and business logic that makes more easier to write test codes.

GithubRepository

4. Configuring the PreferenceRoom

In case to persist so simple data like username or the last selected menu position, then SharedPreferences are the good alternative to persist data.

I already posted before, PreferenceRoom is for management SharedPreferences more efficiently. It was inspired by Room Persistence and dagger. It supports putter & getter custom functions with security algorithm and put & get objects.

Profile Entity

Firstly, we should create an Entity with @PreferenceEntity annotation.

PreferenceComponent

And next, we should create Preference Component and add targets where to injecting dependencies.

PreferenceComponent Injecting

Finally, we can request dependency injection using @InjectPreference annotation after initializing components or entity.

Preference_UserProfile

PreferenceRoom is based on annotation processor so it creates class file during the compile time.

5. Configuring the DataBinding

The Data Binding Library offers both flexibility and broad compatibility — it’s a support library. DataBinding binds model with xml layout files, so it makes we should not to write messy UI codes on ViewHolders and activities.

Build Environment

add below code on your Gradle file. then setting is done!

android {

....

dataBinding {

enabled = true

}

}

then setting is done!

item_history.xml

This is a simple history item xml layout. As you can see, it has data tag at the head.

HistoryViewHolder

This is a History item’s ViewHolder. drawItemView method binds history data to ItemHistoryBinding.

6. Configuring the RecylcerView Paginator

Sometimes we need to implement endless scroll or paging recyclerView.

So I searched about paging library and I found one by Google.

But It’s only supports paging data from database. So our team implemented RecyclerViewPaginator.

RecyclerViewPaginator

RecylcerViewPaginator performs invoke loadMore when recyclerView needs to load more items. And it would not be called when fetching from network or loading ended.

This is the mainly used architecture in my company’s project!

Of course, I think there are no the best architecture on every projects.

But I think this architecture was really great in my case.

Thank you for reading!