3 ways to generate money from your mobile apps

Picture1.pngThe trend for revenue generated from mobile apps is constantly growing and is projected to reach $188 billions for the year 2020 (according to statista).

Today, I want to discuss the three most common options to generate money from apps and which you can already make use of if you have some traffic. I won’t include business specific solutions or selling of physical products outside of apps. So what are these three options?

 

1. Paid Apps

This requires the developer to publish a Paid app into the App Store or Playstore. It is most commonly used for apps by high profile company or apps which the customer already know what to expect from.

 

2. In-app Purchases

There are 3 types of in-app purchases:

Subscription – The user will either need to pay a monthly/yearly subscription feeAt the end of subscription period the user will have the option renew paid service. Note that, you can also allow the user to have trial periods (e.g a week) before a required subscription to continue to use the app.

Consumable – These are features within the app which the user is required to pay every time he wants them. The purchased item will get “consumed” at some point in time inside the app. Then the user will decide if he wants to pay again to get back the consumable item. An example of this would be buying extra-health in a game.

Non-consumable – These includes purchases which the user is expected to make only once in your app. After the purchase, the non-consumable item can be use at any point in time and on any other devices with the same Apple ID/Google Account. Some examples includes: “Upgrade an app to pro edition”, “Remove ads”, “full game unlock”.

 

3. Ads

Now the third option is to display ads inside of you app. There are 3 format of ads commonly used for mobile apps:

Banner ads – are rectangular images or texts that occupy a specific spot inside your app screens. They normally stay on screen while users are interacting with your app.

Interstitial ads – are full-screen ads that cover the interface of your app. They’re displayed at natural transition points in the flow of an app, such as during the pause between levels in a game.

Rewarded video ads – are full-screen video ads that users have the option of watching in exchange of in-app rewards.

 

Conclusion

As you can see, there is a high amount of money being consumed from within of apps. When designing a new app, do take these into consideration to make sure you have a successful business.

Cheers.

 

Reverse Engineering an App & enabling Proguard – Android Security

Let’s Reverse Engineer an Android App

Did you obfuscate app before releasing your APK file to the Playstore?

Please make sure you do, otherwise, consider that anyone can reverse engineer your app source code. Just as a matter of fact, I recently had to reverse engineer an APK. Why? Our partner who developed our app did not want to give us the source code which we legally owned. Fortunately, we only used it to troubleshoot an issue with the app.

Indeed, the process to get the source code from an unprotected APK is quite straightforward.

– Download the APK file

The first step is to obtain the APK file. Search for the APK of the app from this website https://apkpure.com.

– Use deobfuscation tools to reverse engineer the APK file

We will use an online tool: http://www.javadecompilers.com/apk. For e.g, after uploading the MyEmtelApp APK into javadecompilers.com,  we can see all extracted source codes:

Screen Shot 2019-01-30 at 9.23.57 PM.png

We can obtain everything from sources folder (Java codes) to resources (string.xml files, layout files). For example, in the MyEmtelApp above listed is all the packages in the app module. Indeed, if we go into each package, we will obtain the complete source code for each class. Thankfully, we can choose to secure the APK file without too much effort. There exists various options but we will be using Proguard tool in our example.

Securing your code

As we have seen the side effect of not using proguard, let’s now look at the effort required to protect your APK.

will also remove unused code and also optimises the byte code, thereby reducing the size of APK build. However, we cannot obfuscate all code in our app, this may usually cause unexpected behaviors. It is critical to test (or retest) any release build whenever proguard is enabled.  To prevent issues, we will need to explicitly tell proguard which code NOT to obfuscate and this is usually done in the ‘proguard-android.txt’ file. Let’s see the process to enable proguard in Android Studio:

a) Enable Proguard for RELEASE build:

  • Open build.gradle of the app module.
  • Update the “buildTypes” for the release build as below:
    Screen Shot 2019-01-30 at 5.31.55 PM.png
  • Add the line minifyEnabled true
  • Add the line to set the proguard rules:

proguardFiles getDefaultProguardFile(‘proguard-android.txt’), ‘proguard-rules.pro’

After updating the gradle file, try to generate a release APK. You may get some warnings which is normal. If you find errors like “ClassNotFoundExceptions“, you will need to update your proguard rules which we are now going to discuss.

b) Add proguard Rules!

Proguard will obsfuscate all your code which may cause some issues. You must update your proguard rules file to prevent potential app crashes.
First, locate the file “proguard-rules.pro”:
Screen Shot 2019-01-30 at 7.08.58 PM.png
In the file, proguard-rules.pro we will add the lines below for all errors ClassNotFoundExceptions, MethodNotFoundException, FieldNotFoundException which we got when building the release APK in the previous section:
-keep class {MISSING_CLASS_PACKAGE_NAME.**}
-dontwarn {MISSING_CLASS_PACKAGE_NAME.**}

 

What classes we need to keep?

Usually we have to add the keep annotation for all classes which uses reflection. These are classes which are Serialized and Deserialized to transform an object of class into another format. E.g, Data classes in HTTP requests; turning JSON objects into data objects.  This is required because Android/JRE needs to access the class at runtime to compute how to transform the object.

If you do not add @keep annotation, you will find your models will no represented in the proper format after Serializing/Deserializing. Below is an example how to add exception into proguard-rules.pro file to prevent models in “myapp.com” package from being obfuscated.

-keep class myapp.com.model.** { *; }  -> simply means all classes inside model package will not be obsfuscated as we need to keep data models which are serialised.

# Application classes that will be serialized/deserialized over Gson, keepclassmembers
-keep class myapp.com.model.** { *; }
-keepclassmembers class myapp.com.model.** { *; }

 

Consequently, there are external libraries which requires proguard exception. E.g all libraries which uses reflection, e.g Gson, OKHttp, ROOM Dao, Firebase.

# For using GSON @Expose annotation
-keepattributes *Annotation*

#bottom navigation
-keep public class android.support.design.widget.BottomNavigationView { *; }
-keep public class android.support.design.internal.BottomNavigationMenuView { *; }
-keep public class android.support.design.internal.BottomNavigationPresenter { *; }
-keep public class android.support.design.internal.BottomNavigationItemView { *; }

#OKHTTP
-keep class com.squareup.okhttp.** { *; }
-keep interface com.squareup.okhttp.** { *; }
-dontwarn com.squareup.okhttp.**
-keep class com.android.okhttp.** { *; }

#Android Room
-keep class myapp.com.persistence.** { *; }
-dontwarn android.arch.util.paging.CountedDataSource
-dontwarn android.arch.persistence.room.paging.LimitOffsetDataSource

 

After adding all the required @keep and @dontwarn annotation, you should build and run your release APK without any issue. This should prevent easy deobfuscation of your app through various reverse engineer techniques. Note that this will also help reduce your APK size. That will be all for this blog post. I hope this helps you to better understand to better secure your APK. Feel free to comment if you encounter any issue.

Follow my blog for more tips & tricks when developing your mobile apps.

 

 

Two-Way Data binding in Android

Two-way data binding is a way to update your Views attributes using Observable objects and vice-versa. In Android framework you would essentially define an observable object which would notify your views (e.g EditTexts) whenever it is updated. The term “Two-way” means that whenever your views are updated, your observable object would also get updated. This design pattern allows for loose coupling between your Android layout and your Activities/Fragments. It is often used in MVVM pattern.

Without further due, let’s develop our data binding app. By default, data binding is not enabled in a new project. Let’s start with enabling data binding:

Update build.gradle for app module (Module: app)

Inside of “android {} ” tag add the code:

dataBinding {
    enabled = true
}

 

The result build.gradle (Module: app) should be as below  :

android {
    compileSdkVersion 27
    defaultConfig {
        applicationId "devanshapps.databindingexampleapp"
        minSdkVersion 17
        targetSdkVersion 27
        versionCode 1
        versionName "1.0"
        testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
    }
    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }

    dataBinding {
        enabled = true
    }
}

Note enabling data binding will actually import the android.databinding support library 

 

Our App Design

For this example, we will have a simple design with a list of EditText inputs as below:

Screen Shot 2018-10-06 at 8.49.05 PM.png

 

Enabling Data Binding in a layout file

To enable data binding you would need to update your root/parent view to “layout” tag:

<?xml version="1.0" encoding="utf-8"?>
<layout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools">

    <android.support.constraint.ConstraintLayout 
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        tools:context=".MainActivity">

        <EditText
            android:id="@+id/edt_firstname"
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_marginEnd="8dp"
            android:layout_marginStart="8dp"
            android:layout_marginTop="8dp"
            android:ems="10"
            android:inputType="textPersonName"
            android:text="First Name"
            app:layout_constraintEnd_toEndOf="parent"
            app:layout_constraintStart_toStartOf="parent"
            app:layout_constraintTop_toTopOf="parent" />

         .
         .
         .
    </android.support.constraint.ConstraintLayout>
</layout>

 

Accessing views from Java

You will first need to “Build” your project so that the required “data binding” classes get generated. In our case, since our layout file name is “activity_main.xml”, the class ActivityMainBinding will get generated.

In our MainActivity.class, you will need to replace “setContent(R.layout.activity_main);” with the generated ActivityMainBinding. The result will be as below:

public class MainActivity extends AppCompatActivity {
    ActivityMainBinding binding;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);
        binding = 
          DataBindingUtil.setContentView(this, R.layout.activity_main);
    }
}

If all is setup properly, you should be able to access EditTexts defined from “binding” object itself as below:

private void setViews() {
    binding.edtFirstname.setText("Bob");
    binding.edtSurname.setText("Dylan");
}

Note: We are not there yet with regards to our actual two-way data binding!

 

Create an Observable class for UI data fields:

Our observable object needs to extend “BaseObservable” from data binding library “android.databinding.BaseObservable

First we will add all of the required fields in our layout file:

public class User extends BaseObservable {
    private String firstName;
    private String surname;
    private String jobTitle;
    private String hobbits;
}

 

Add a reference to the User data object in the layout file:

In our activity_main.xml we will now need to add a reference to the User class as below:

<?xml version="1.0" encoding="utf-8"?>
<layout>
    <data>
        <variable
            name="data"
            type="devanshapps.databindingexampleapp.User"/>
    </data>
    
    <android.support.constraint.ConstraintLayout
    .
    .
</layout>

 

We will also need to add a reference to the attributes e.g firstName, surname, jobTitle, hobbits:

<EditText
    android:id="@+id/edt_firstname"
    android:layout_width="0dp"
    android:layout_height="wrap_content"
    android:layout_marginEnd="8dp"
    android:layout_marginStart="8dp"
    android:layout_marginTop="8dp"
    android:ems="10"
    android:inputType="textPersonName"
    android:text="@={data.firstName}"
    app:layout_constraintEnd_toEndOf="parent"
    app:layout_constraintStart_toStartOf="parent"
    app:layout_constraintTop_toTopOf="parent" />

<EditText
    android:id="@+id/edt_surname"
    android:layout_width="0dp"
    android:layout_height="wrap_content"
    android:layout_marginEnd="8dp"
    android:layout_marginStart="8dp"
    android:layout_marginTop="12dp"
    android:ems="10"
    android:inputType="textPersonName"
    android:text="@={data.surname}"
    app:layout_constraintEnd_toEndOf="parent"
    app:layout_constraintHorizontal_bias="0.0"
    app:layout_constraintStart_toStartOf="parent"
    app:layout_constraintTop_toBottomOf="@+id/edt_firstname" />

<EditText
    android:id="@+id/edt_job_title"
    android:layout_width="0dp"
    android:layout_height="wrap_content"
    android:layout_marginEnd="8dp"
    android:layout_marginStart="8dp"
    android:layout_marginTop="16dp"
    android:ems="10"
    android:inputType="textPersonName"
    android:text="@={data.jobTitle}"
    app:layout_constraintEnd_toEndOf="parent"
    app:layout_constraintHorizontal_bias="0.0"
    app:layout_constraintStart_toStartOf="parent"
    app:layout_constraintTop_toBottomOf="@+id/edt_surname" />

<EditText
    android:id="@+id/edt_hobbits"
    android:layout_width="0dp"
    android:layout_height="wrap_content"
    android:layout_marginEnd="8dp"
    android:layout_marginStart="8dp"
    android:layout_marginTop="12dp"
    android:ems="10"
    android:inputType="textPersonName"
    android:text="@={data.hobbits}"
    app:layout_constraintEnd_toEndOf="parent"
    app:layout_constraintHorizontal_bias="0.0"
    app:layout_constraintStart_toStartOf="parent"
    app:layout_constraintTop_toBottomOf="@+id/edt_job_title" />

 

Getters and Setters for data binding object

Note that we want to have two observers in our case; our User object observing the Views (activity_main.xml) and the Views observing the User object in java.

We will need to add the annotation “@Bindable” to the “Getter” method which is from the data binding library (“android.databinding.Bindable”). This will allow our layout file to get the value of the property  by using the getter methods.

After adding the “@Bindable” annotation to all of the fields’ Getters, build the project. This will generate BR.firstName, BR.surname, BR.jobTitle, BR.hobbits).

Call the method notifyPropertyChanged(BR.field_name) inside of the setter methods so that the views are now notified whenever a field in the user object updated. The resulting user class will look like below:

public class User extends BaseObservable {
    private String firstName = "";
    private String surname = "";
    private String jobTitle = "";
    private String hobbits = "";

    @Bindable
    public String getFirstName() {
        return firstName;
    }

    public void setFirstName(String firstName) {
        this.firstName = firstName;
        notifyPropertyChanged(BR.firstName);
    }

    @Bindable
    public String getSurname() {
        return surname;
    }

    public void setSurname(String surname) {
        this.surname = surname;
        notifyPropertyChanged(BR.surname);
    }

    @Bindable
    public String getJobTitle() {
        return jobTitle;
    }

    public void setJobTitle(String jobTitle) {
        this.jobTitle = jobTitle;
        notifyPropertyChanged(BR.jobTitle);
    }

    @Bindable
    public String getHobbits() {
        return hobbits;
    }

    public void setHobbits(String hobbits) {
        this.hobbits = hobbits;
        notifyPropertyChanged(BR.hobbits);
    }
}

Cool. We are almost done. Note that we have to add the “@Bindable” annotation to the Getter method first so that the associated “BR” fields are generated.

 

Instantiate the UI Data model inside your Activity or Fragment:

Inside of our MainActivity, we will instantiate the User object and pass it on the the DataBinding (binding) object:

public class MainActivity extends AppCompatActivity {
    ActivityMainBinding binding;
    User data = new User();

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        binding = DataBindingUtil.setContentView(this, R.layout.activity_main);
        binding.setData(data);
    }
}

 

Done!

You should  now able to reflect any changes from the the User object to the Views and any user inputs to reflect into the User Object (UI model). This allows our Activity (or Fragment) to manage view data directly from the UI object with little coupling with the View (layout file). For instance, the MainActivity does not need to know if “firstName” is an EditText or a TextView (type of view), changing the EditText to TextView will not require any change inside of MainActivity or User Object Model.

I have added the following code in the example project to showcase the two-way data binding in action:

private void setViews() {
    data.setFirstName("Bob");
    data.setSurname("Dylan");
}

public void printData(View view) {  // onclick on "Print" button listener
    Log.i(MainActivity.class.toString(),
            "User data: "  + data.getFirstName() + " " + data.getSurname()
                    + " works as " + data.getJobTitle() + " and likes to " + data.getHobbits());

}

 

Basically the Activity will load with the fields “first name” and “surname” set to “Bob” and “Dylan”. Also I have added button “Print” which will get updated values of EditTexts from the User object after the user has changed fields values. The complete source code for the example project is available on github: https://github.com/devansh-ramen/Two-Way-DataBinding-Android

That will be it for this post on “Two-way” data binding. There are few additional tweaks which may be are required for e.g, to use “Spinner” views or to add String Utils method (e.g formatting values) displayed in views. But this might be a good topic for another blog post. We have covered the basic to get started and running with the two-way data binding. This should already help to make our code cleaner and faster to debug/develop. As always happy coding. You can always let me know if you are getting stuck in some related issues.

Cheers.

Regards,

 

Review ‘Strapi’ as CMS/API solution for mobile apps

If you need a quick and easy solution for your backend APIs + a CMS, I would recommend you to have a look at Strapi.io. The solution near zero coding to get started.

The project comes by default with APIs for Login, forget password, Registration, Login via Social Medias. All the APIs are secured OAuth. Another great feature is that you can create your schemas which can include relationships, and media type from the Admin portal itself (from web interface).  Based on the defined schemas, Strapi will automatically generate APIs to:

  1. Get a list of all objects from any schema (including nested objects/relationships)
  2. Search for one object based on its ID
  3. Count the number in any schema/table
  4. Create a new object for any schema
  5. Updated a record
  6. Delete a record

 

The CMS generated has a clean design, very easy to use on Desktop. Of course you can modify or add any APIs or the CMS interface. The generated APIs using NodeJS and the CMS uses React.JS. All React codes for the CMS web interface is store inside of “admin” folder while all of the APIs generated is stored inside of api folder.

 

There are a few downside:

Strapi is still in Alpha stage; some features may not work properly. I recently found out that fields of type images of child objects are not properly populated from APIs. However I found solution from their github which required a few modification in generated codes.

Strapi CMS is not responsive for mobile and is pretty much limited for Desktop only.

 

For more details, checkout Strapi official website: https://strapi.io

 

Best Regards

Enjoy

Introduction to Kotlin for Android Developers

At Google I/O 2017, the Android team at Google announced Kotlin as the official language for Android development. With this update, Android developers can now enjoy the features of a more modern programming language. That said, Android developers are not forced to used Kotlin and can keep using Java which is still supported.

Why using Kotlin?

  • Interoperability: Kotlin is a JVM base language, it is fully ‘inter-operable’ with Java. This means we can have Kotlin code can co-exist with Java code and vice versa.
  • Kotlin is a programming language developed by JetBrains, same company who developed IntelliJ. Android Studio IDE is based on IntelliJ.framework.
  • Modern programming language fully supported. All the features of Java 1.8 are not available when developing using Android SDK (if need to support lower version of Android).
  • Safer: Deal with null pointer at compile time. Preventing null pointer exceptions is much easier.
  • Expressiveness: Kotlin will in many case involve writing less code for solving same problem.

Before going deeper into these new features, lets start from basic.

 

Variables

Mutable Object

In Java, we would have following code to represent a mutable object of type String

String mObject = "Hello World";

 

This would be the equivalent in Kotlin:

var mObject: String = "Hello World"
  • The “var” keyword is used for mutable type object.
  • The type of the object (String) is specified before its name (mObject) You can think of it as mObject “extends” String. (e.g, mObject: String )
  • Semi-colon is optional in Kotlin.

Inferred Type

However, we can simplify the code as Kotlin can automatically Infer type of the object. Kotlin can infer the type of the object based on the value which it is set to. For example, since we are assigning the string “Hello” to the object, we don’t need to specify its Type:


var mObject = “Hello”

If now, we instead integer value “10”,  Kotlin will infer the Type of the object as Int


var mObject = 10

 

Immutable Object

An immutable object is one whose value is set once and cannot be changed. In Java, we are used to the keyword “final” to describe an immuatable object:


final String MOBJECT = "Hello World";

The “val” keyword is used to describe a immutable in Koltin:


val contantObject = "Hello World"

The general good practice is to always use immutable as far as possible. This makes code more predictable and will be important when working with Null safety feature which we will look into the next section.

 

Null safety feature

A common crash in many programming languages (including Java) is when accessing an attribute or method of a null reference. In Java this would result in a crash equivalent of a NullPointerException (NPE).  This error is also known as The Billion Dollar Mistake.

Kotlin’s type system is designed to prevent NullPointerExceptions.


val strOptional: String? = null

strOptional?.length

This is equivalent to following in Java:


if (strOptional != null)

    strOptional.length()

strOptional?.length: If and only if the object strOptional is not null, will the length method be call

Note that the “?” is required for the code/project to compile. We can use not-null assertion operator (!!) as below to force the code to compile, however in the above scenario, it would result in a NPE.


strOptional!!.length

 

Classes

Classes in Kotlin are declared using keyword class. We will create a Class which extends Activity from Android SDK.


class MainActivity: Activity {}

This would be equivalent of following in Java:


final class MainActivity extends Activity {}

Classes are closed by default which is equivalent of “final” in Java. So we won’t be able to extend the class “MainActivity” in another class. To make the class extendable, we have to explicitly declared class as open or abstract:

open class BaseActivity: Activity {}

MainActivity can extend BaseActivity of if BaseActivity class is “open”:

class MainActivity: BaseActivity {}

 

Data classes & Properties

Kotlin provide Data type classes and Properties which avoid many boilerplate which would be required in Java which creating POJO classes. Properties are equivalent to fields in Java but which includes getters and setters. However in Kotlin, we don’t need to explicitly declare getters and setters, it will be automatically created under the hood.

Let’s say we have a User model which requires the following attributes (properties in kotlin): “firstName” and “surname

public class User {
    private String firstName;
    private String surnameName;
    private String mood;

    public String getFirstName() {
        return firstName;
    }

    public void setFirstName(String firstName) {
        this.firstName = firstName;
    }

    public String getSurnameName() {
        return surnameName;
    }

    public void setSurnameName(String surnameName) {
        this.surnameName = surnameName;
    }

    public String getMood() {
        return mood;
    }

    public void setMood(String mood) {
        this.mood = mood;
    }
}

We can have the above class with only 1 line in Kotlin by using “data” class  contain firstName and lastName properties:

 data class User(val firstName: String, val lastName: String, val mood:String) 

Kotlin will generate the generic getters and setters methods under the hood for properties. That will allow us to write less and also make it easier to manage changes.

 

Instantiating an object

When instantiate an object in Kotlin, we don’t need to specify the “New” keyword each time as in Java:


val user = User("Frank", "Einstein", "happy")

 

Data classes come with some  handy functions:

  • copy() -> This is handy if we are using immutable objects.

A general practice is to use immutable objects when possible to avoid unexpected changes from other part of our code. e.g,


val user = User("Frank", "Einstein", "happy")

val userUpdated = user.copy(mood = "angry")

  • equals() -> compare all properties of object to another to make sure they are identical:
user.equals(userUpdated) // false since Frank's mood has changed

 

Functions

Let’s create a small function which takes two integers and return their sum in Java:


private void sum(int x, int y) {
    return x + y;
}

In Kotlin, functions are declared using the “fun” keyword. Parameters will be

fun sum(x: Int, y: Int): Int {
   return x + y
}

Note that for the parameter X or Y, we write the Name first, then its Type. The return type (Int) is at the end just before function body.

If the result can be calculated in a single expression we can omit the curly braces and simply specify the function body after “=” symbol as below:

fun sum(x: Int, y: Int): Int = return x + y

 

Higher-order function

Functions are first class citizen in Kotlin, which means function can be passed as variable, arguments or return from other functions. We will store same sum function into an object using lambda expressions as below:

val sum = { x: Int, y: Int -&amp;gt; x + y }
  • A lambda expression in Kotlin is surrounded by curly braces {}
  • the code before the “->” sign x: Int, y: Int  is parameter declaration for our function
  • the code after the “->” sign is the body of the function
  • the return type is automatically inferred with Kotlin as we already know the parameter is of type int, the expression will return and Int

 

Extension Function

Another interesting feature with Kotlin (and other modern programming language) is Extension function. If you are new to this concept, I will try to explain you the concept by using components from Android SDK.

Imagine you want to have a method for all your Activity classes. In Java, we would create a “BaseActivity” class which will have the required method implementations, and then have all of our activities extend that BaseActivity and inherit the method. Kotlin provides a special feature known as Extension Function. Instead of base calls, a static method will be created and made available to the existing Activity class from the Android SDK:

fun Activity.toast(message: CharSequence, duration: Int = Toast.LENGTH_SHORT) {
    Toast.makeText(this, message, duration).show()
}
  • Note parameter default value is used for Duration parameter: duration: Int = Toast.LENGTH_SHORT
  • “this” -> refers to the Activity itself. Inside of the Extension we will have all methods which are accessible from the Activity class. For e.g getApplicationContext().

 

That works like magic. The extension function can be written anywhere in our project. I understand Kotlin basically generates a static method which is made available to actual Activity class:

class MainActivity : Activity(), MainContract.View {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        toast("this is toast from extension function")
    }

}

Extension function is very useful if we want to add a function into a code base which we cannot modify class inside of Library and Android SDK.

The Kotlin team developed a robust library for Android which implements many useful extension functions: https://github.com/JetBrains/anko which basically “adds” new features to Android Framework. It might be worth looking into.

 

Conclusion

Kotlin is similar to Java, it runs on JVM and is fully supported by Android Studio. I would say it’s a must for Android developers to give it a try. There are indeed many new features some which I covered in this blog post. I hope this is helps you started to get into Kotlin language. In future blog posts, I may go deeper inside specific features which I find useful. You can always  keep in touch by clicking on “Follow” button at the bottom right corner. Stay blessed. Cheers

MVVM – Android’s Architecture Components Part 2 – Repository Pattern

In the Part 1 of Android Architectural Component series, we have implemented two-way data binding and explained the Android Architectural components: ViewModel and Live Data, and LifeCycleOwner. However, the data layer part of the app was not complete, more specifically we did not implement the Repository Pattern. The previous example did not have a persistence solution to cache data from API. This might be required in many use cases for following reasons:

  1. User experience: making the user wait for some data is bad user experience, when possible, it needs to be avoided
  2. Data needs to be persisted: user needs to login once
  3. Waste of network resource: re-fetch same data
  4. Data lost: Flaky network can prevent you from obtaining data anytime
  5. Android OS/GC can clear data which is store in memory anytime.

In this blog post, we will go through the detail of our open source example of the MVVM android app implementing the Architectural Components guideline. Since this guideline was released only year, I did not find many open source project which is complete. Our example follows the Android App Guideline as strictly as possible and the source code is easy to understand:

Persistence data using Room DAO & LiveData

The Android Architecture Components provides a library to persist data: Room DAO. In a previous blog post, we have discussed about how to setup the Room Persistence Library: https://devanshramen.com/2017/09/20/intro-to-room-persistence-library/. Feel free to go back to this if you haven’t used Room before.

@Dao
public interface UserDao {
    
    @Query("SELECT * FROM user LIMIT 1")
    LiveData<User> getUser();

    @Insert
    (onConflict = OnConflictStrategy.REPLACE)
    void insert(User user);

    @Delete
    void delete(User user);

    @Query("DELETE FROM user")
    void deleteAll();
}

 

  • Returning LiveData

@Query(“SELECT * FROM user LIMIT 1”)
LiveData<User> getUser();

LiveData as mentioned in Part 1 of Android Architectural Component will notify any of its observers when its value changes. For instance, in our login example, the user entity will be updated when the Login API operation is successful (user will be inserted into user entity).

 

Fetching Data from Webservice

In the blog post, we were calling Login API operation inside of our ViewModel. We marked this part TODO and rightly so. Other than not providing a Persistence solution, the ViewModel is responsible for holding Data for the Activity and Fragment. Fetching data inside the ViewModel would violate the Single Responsibility Principal. This would make our app more difficult to maintain as it is scaled when new features are added. We will have a new class “UserRepository” to manage all operations which are at the “data layer”. (Note that we are using a mock api and does not include any authentication or use of token for this example in which we won’t go through this part)

 

UserRepository

The Repository class (modules if we use dagger2), will manage data which is being cached local repository or which needs to be sent to a remote repository (through web service). The UserRepository is using Room (userDao) and Retrofit for remote data.

public class UserRepository {
    UserDao userDao;
    Executor executor;

    public UserRepository() {
        this.userDao = AppDatabase.getAppDatabase(MApplication.context).userDao();
        executor = Executors.newSingleThreadExecutor();
    }

    public void clearUserCached() {
        executor.execute(() -> {
            userDao.deleteAll();
        });
    }

    public void loginUser(String email, String password) {

        getAPIService().login(new LoginRequest(email, password))
            .compose(RxUtils.applySchedulers())
            .subscribe(
                (LoginResponse response) -> {
                    executor.execute(() -> {
                        userDao.insert(response.getUser());
                    });
                },
                (Throwable e) -> {
                    e.printStackTrace();
                }
            );
    }

    public LiveData<User> getUser() {
        return userDao.getUser();  
    }
}

  • loginUser(String email, String password): 

We have now exposed a method for network call to perform the login operation inside of the UserRepository. The key point here is that when the operation is successfully we will update the RoomDao:

executor.execute(() -> {
    userDao.insert(response.getUser());
});

(note that the i/o operation for Room needs to be done in background thread – thereby use of executor)

 

  • LiveData<User> getUser(): 

Our LoginViewModel will setup its UserResponse LiveData attribute with this method such that the LiveData for User Entity in Room DAO will be used to detect if user data was updated.

 

  • Optimise code with Dependency Injection:

Note that we can optimise this class for scalability by using Dependency Injection to provide for UserDAO with a single implementation and thereby avoid some code duplication.

 

Updated LoginViewModel

public class LoginViewModel extends ViewModel {

    // Create a LiveData
    private LiveData<User> userResponse;

    public final ObservableField<String> email = new ObservableField<>();
    public final ObservableField<String> password = new ObservableField<>();

    public final ObservableField<String> errorEmail = new ObservableField<>();
    public final ObservableField<String> errorPassword = new ObservableField<>();

    UserRepository userRepository;

    public LoginViewModel() {
        userRepository = new UserRepository();
        userResponse = userRepository.getUser();
    }

    public LiveData<User> getUser() {
        return userResponse;
    }
    
    public void onBtnLoginClick() {
        if (validateInputs()) {
            userRepository.loginUser(email.get(), password.get());
        }
    }
   .
   .
   .
}

We were previously using an observable on LoginResponse. This has been updated to use LiveData and the UserRepository which has the implementation for calling login API and which can talk to UserDao. Note that the updated ViewModel will not have any implementation for fetching cached data or data from a Web service.

  • Subscribe to UserDao from UserRepository

The method getUser() from UserRepository returns the LiveData<User> from UserDao:

public LoginViewModel() {
    userRepository = new UserRepository();
    userResponse = userRepository.getUser();  
}

 

The LoginViewModel exposes the LiveData to the LoginActivity so that the Activity can take UI actions should the data in UserDao be updated:

public LiveData<User> getUser() {
    return userResponse;
}

 

  • Calling Login method from UserRespository: 
public void onBtnLoginClick() {
    if (validateInputs()) {
        userRepository.loginUser(email.get(), password.get());
    }
}

 

LoginActivity – User Observer

The Login will remain same as before but now we will get user object instead of LoginResponse. It will also be notified in theory of changes from UserDAO instead of actual Login API.

// The observer updates the UI when UserDAO is updated
mViewModel.getUser().observe(this, userResponse -> {
    if (userResponse != null) {
        Toast.makeText(LoginActivity.this, "Login success", Toast.LENGTH_SHORT).show();

        Intent intent = new Intent(this, MainActivity.class);
        startActivity(intent);
        finish();

    } else {
        Log.d("LoginActivity", "value user is null");
        // Show ERROR
    }
});

 

MainActivity

For the sake of the example, we have added a MainActivity class which will display the user’s details. The data will be retrieved directly from Room UserDAO without requiring to make another API call to fetch data. It also shows that the data was successfully cached.

  • Display cached User Details: 
// The observer updates the UI to display prefetched user details
mViewModel.getUser().observe(this, userResponse -> {

    if (userResponse != null) {
        binding.txtWelcome.setText("Welcome " + userResponse.getFirstName() + " " + userResponse.getLastName()
                + "\n\n" + "You are more than a " + userResponse.getJobTitle());

    } else {
        logoutUser();
    }
});

 

MainViewModel

The MainViewModel will also make use of the same method (userRepository.getUser()) from UserRepository to get cached user:

public class MainViewModel extends ViewModel {
    private UserRepository userRepository;

    public MainViewModel() {
        userRepository = new UserRepository();
    }

    public LiveData<User> getUser() {
        return userRepository.getUser();
    }

    public void clearUserData() {
        userRepository.clearUserCached();
    }
}

Conclusion:

That’s it, we have now implemented the Repository Pattern and completed the Part 2 of our MVVM using new Android Architectural components. Please find the full project source below:

https://github.com/devansh-ramen/Android-App-Architecture-MVVM

Do not forget hit the “Star” button on the project repository:

If you have any queries, feel free to post a comment in the Comment section below, I will respond to you as soon as possible.