Implementing In-app Update in Android

In-app update in Android is one of the most powerful feature that android has introduced in recent times.

This tutorial is broken down into two parts for easy understanding and no mixups.

Understanding In-App updates

Before we dive into the actual implementation of in-app updates. Let us first understand why it is necessary in the first place.

Most of the users of application might have turned on background auto updates. The normal update procedure might work flawlessly in such cases. But there might be some cases when the user might have turned auto update off. Or for some other reason they might not update their application.

So this in-app update feature will help the developer to deliver the latest fixes to active users in a streamlined way.

This feature is introduced by Android as a part of their Google Play Core libraries. And it is supported from Android 5.0 ( Lollipop ) onward.

Also there is one more thing to note, if the APK uses .obb expansion files then in-app update is not compatible.

Types of In-app updates in Android

Now that brings us to the next portion of our post. The types of in-app updates in Android.

There are two types of in-app updates in Android:

Flexible updates

If your application is in need of an update, but the update is not critical or essential for its functionality, you have the option to decide whether to apply this particular update or not. As users will be able to dismiss the popup for the in-app update and continue using the application.

This means that if the update is not necessary for the proper functioning of your application, you can choose whether or not to install it. Because these kind of in-app update can be dismissed by user in as it is displayed in a popup.

See image below for reference ( image taken from Android official website )

Immediate updates

If your application needs a critical update that is vital for its core functionality, you can choose to use this kind of update. However, it’s important to note that during the process of downloading and applying the update, the application will display a full-screen user interface to ensure that the process isn’t interrupted.

This means that until the update is fully downloaded and implemented, the application will occupy the entire screen. And when everything is completed the application will automatically restart.

This update cannot be dismissed by the user once shown to them. ( image taken from Android official website )

How to implement in-app updates in Android?

Let us now look into both of these in-app update types by implementing them.

Before we go ahead with the implementation we have to decide a proper use-case for each of the in-app update.

Flexible in-app update

Let us implement flexible in-app update step by step as shown below

Step #1: Adding play core dependency

Add the following dependency in the app > build.gradle file and sync it.

implementation 'com.google.android.play:core:1.10.3'Code language: JavaScript (javascript)

Please consider checking and using the latest version of library from this link.

Step #2: Create AppUpdateManager instance

First we need to create a new method named initFlexibleUpdate(). And inside the method we will instantiate a new object of AppUpdateManager class.

This class will help us move forward with our flexible update implementation.

private void initFlexibleUpdate() {
    // create app update manager instance
    AppUpdateManager appUpdateManager = AppUpdateManagerFactory.create(this);
}Code language: JavaScript (javascript)

Step #3: Check whether new update is available

Next, we will have to check if a new update is available in the Google Play Store. The logic for checking is provided below.

private void initFlexibleUpdate() {
        // create app update manager instance
        AppUpdateManager appUpdateManager = AppUpdateManagerFactory.create(this);

        // we have to get information whether the update is available or not
        Task<AppUpdateInfo> appUpdateInfo = appUpdateManager.getAppUpdateInfo();
        appUpdateInfo.addOnSuccessListener(new OnSuccessListener<AppUpdateInfo>() {
            @Override
            public void onSuccess(AppUpdateInfo appUpdateInfo) {
                // check the number of days the app update has been available in the play store
                Integer numberOfDays = appUpdateInfo.clientVersionStalenessDays();

                boolean isUpdateAvailable = appUpdateInfo.updateAvailability() != UpdateAvailability.UPDATE_AVAILABLE;
                boolean isUpdateThresholdMet = ((numberOfDays == null ? -1 : numberOfDays) >= 1);
                boolean isFlexibleUpdateAllowed = appUpdateInfo.isUpdateTypeAllowed(AppUpdateType.FLEXIBLE);
                if (isUpdateAvailable && isUpdateThresholdMet && isFlexibleUpdateAllowed) {
                    // Update is available
                    
                } else {
                    Log.d("FlexibleUpdateTechenum", "onSuccess: update is not available.");
                    // Update not available, handle accordingly
                }
            }
        });
}Code language: JavaScript (javascript)

Let us look at what’s happening in the code above.

  • First, we get AppUpdateInfo from the AppUpdateInfo. This is of Future type on which we added .addOnSuccessListener(), here we will get notified once the check is complete.
  • Next, we will get the staleness days for this application. In simple words this means that we will get a positive response if this much days have passed since the update is made live.
  • Next, we have three variables isUpdateAvailable , isUpdateThresholdMet and isFlexibleUpdateAllowed. Each of the variable is self explanatory we move forward only if update is available and stale days are more than mentioned and if flexible update is enabled.
  • Lastly, there is also an else block where you can do something if the update is not available.

Step #4: Start the flexible update

Finally, we have setup all the necessary portions for handling the actual flexible update logic. We will go ahead with downloading and installing the update inside the if block.

An explanation of the code is provided below, please do check it out. Also, the code below is the full code for the initFlexibleUpdate() method.

private void initFlexibleUpdate() {
    // create app update manager instance
    AppUpdateManager appUpdateManager = AppUpdateManagerFactory.create(this);

    // we have to get information whether the update is available or not
    Task<AppUpdateInfo> appUpdateInfo = appUpdateManager.getAppUpdateInfo();
    appUpdateInfo.addOnSuccessListener(new OnSuccessListener<AppUpdateInfo>() {
        @Override
        public void onSuccess(AppUpdateInfo appUpdateInfo) {
            // check the number of days the app update has been available in the play store
            Integer numberOfDays = appUpdateInfo.clientVersionStalenessDays();

            boolean isUpdateAvailable = appUpdateInfo.updateAvailability() != UpdateAvailability.UPDATE_AVAILABLE;
            boolean isUpdateThresholdMet = ((numberOfDays == null ? -1 : numberOfDays) >= 1);
            boolean isFlexibleUpdateAllowed = appUpdateInfo.isUpdateTypeAllowed(AppUpdateType.FLEXIBLE);
            if (isUpdateAvailable && isUpdateThresholdMet && isFlexibleUpdateAllowed) {
                // Update is available
                try {

                    InstallStateUpdatedListener installStateUpdatedListener = new InstallStateUpdatedListener() {
                        @Override
                        public void onStateUpdate(@NonNull InstallState installState) {
                            if (installState.installStatus() == InstallStatus.DOWNLOADED) {
                                // Update has been downloaded
                                // Show some message to the user to restart the application to apply the update
                                appUpdateManager.completeUpdate();
                            }
                        }
                    };
                    appUpdateManager.registerListener(installStateUpdatedListener);

                    // start the update by providing necessary details
                    appUpdateManager.startUpdateFlowForResult(appUpdateInfo, AppUpdateType.FLEXIBLE, MainActivity.this, 111);

                } catch (IntentSender.SendIntentException e) {
                    // Some error occurred
                    Toast.makeText(MainActivity.this, "Could not initiate update request.", Toast.LENGTH_SHORT).show();
                }
            } else {
                Log.d("FlexibleUpdateTechenum", "onSuccess: update is not available.");
                // Update not available, handle accordingly
            }
        }
    });
}Code language: JavaScript (javascript)

Again, let me explain the code above.

  • First, we create a progress update listener this will help us determine the actual status of download. If the download is complete then we will call the appUpdateManager.completeUpdate() which will apply the updates and restart the application.
  • Next, we will call startUpdateFlowForResult() method to start the actual flexible update.
  • Also, if you notice there is a try catch block. This is necessary in case anything wrong happens during any point of our update process.

Step #5: Using initFlexibleUpdate() method

Call this method in the onCreate() of your activity or any place that you want to perform the flexible update.

Conclusion

In 5 easy steps you have implemented flexible in app update from start to finish. Next, we will be looking into immediate updates in Android.

Immediate in-app update

This part will be update in a few days. As this part is completely different therefore I will be implementing this in a separate blog post.

Also Read:

Using Coil image loader for Android

Android Text to Speech (TTS): A simple guide

Android Keystore: Store Sensitive Data in Android

Android Fingerprint Authentication Tutorial: How to Guide

Android Fragments vs Activities

Related Posts