Android Work manager tutorial || Background Services || Periodic Work Request

Android work manager :

In continuation to the previous tutorial we are proceeding with android work manager – periodic work request, i.e., when ever we want to do a work at a periodic interval of time we use this type of work request.

When the work request is initialised and assigned it will complete the task provided.

Even if the app is currently in use or not i.e., in foreground, background or even if the app is killed.

Also need to know that you can’t target a time for any task to be performed. And also instantly perform any task using work manager you may use AlarmManager or Foreground services for those actions.

Also in this blog i am going to provide code in terms of java and kotlin programming language so that it will be easy for you to implement irrespective of language.

 

Work manager periodic work request :

Periodic work request is used to make a background task run in periodic intervals of time making sure it honor’s the android doze mode policy’s in saving the battery life.

Also we can provide several constraints like battery charging level, device is in idle mode or not.

And even internet available is of limited or unlimited so that data is properly used according to the state of availability.

 

Project Structure :

Let us see project structure for android work manager periodic work request

work manager periodic work request project structure

 

Dependency :

We need to add work dependency’s required for android work manager.

def work_version = "2.3.4"
// Kotlin + coroutines
implementation "androidx.work:work-runtime-ktx:$work_version"

// optional - RxJava2 support
implementation "androidx.work:work-rxjava2:$work_version"

// optional - GCMNetworkManager support
implementation "androidx.work:work-gcm:$work_version"

// optional - Test helpers
androidTestImplementation "androidx.work:work-testing:$work_version"

 

Periodic Work Request :

BackgroundTask.class

We need to extend a Worker class to make use of the worker class implementations.

Add a push notification module to let the user know the task status when alarm goes off here we need to take care of android version and handle accordingly.

Kotlin:

Providing the Kotlin source code for android work manager implementation.

import android.app.NotificationChannel
import android.app.NotificationManager
import android.content.Context
import android.os.Build
import android.util.Log.d
import androidx.core.app.NotificationCompat
import androidx.work.Worker
import androidx.work.WorkerParameters

class BackgroundTask (context : Context, params : WorkerParameters)
    : Worker(context, params){
    override fun doWork(): Result {

        d("oneTimeWorkRequest","Uploading photos in background")

        sendNotification("Background Task","Succcessfully done")

        return Result.success()
    }

    private fun sendNotification(title: String, message: String) {
        val notificationManager =
            applicationContext.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
        //If on Oreo then notification required a notification channel.
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
            val channel =
                NotificationChannel("default", "Default", NotificationManager.IMPORTANCE_DEFAULT)
            notificationManager.createNotificationChannel(channel)
        }
        val notification: NotificationCompat.Builder = NotificationCompat.Builder(
            applicationContext,
            "default"
        )
            .setContentTitle(title)
            .setContentText(message)
            .setSmallIcon(R.mipmap.ic_launcher)
        notificationManager.notify(1, notification.build())
    }

}

 

Java :

Providing the java source code for android work manager implementation. You can easily get through the exact implementation of work manager rather than any complicated functionality.

 

import android.app.NotificationChannel;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.content.Context;
import android.content.Intent;
import android.util.Log;

import androidx.annotation.NonNull;
import androidx.core.app.NotificationCompat;
import androidx.work.Worker;
import androidx.work.WorkerParameters;

public class BackgroundTaskJava extends Worker {
    public BackgroundTaskJava(@NonNull Context context, @NonNull WorkerParameters workerParams) {
        super(context, workerParams);
    }

    @NonNull
    @Override
    public Result doWork() {

        Log.d("periodicWorkRequest","Uploading photos in background");

        sendNotification("Background Task","Succcessfully done");

        return Result.success();
    }

    void sendNotification(String title, String message) {
        NotificationManager mNotificationManager =
                (NotificationManager) getApplicationContext().getSystemService(Context.NOTIFICATION_SERVICE);
        if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
            NotificationChannel channel = new NotificationChannel("1",
                    "android",
                    NotificationManager.IMPORTANCE_DEFAULT);
            channel.setDescription("WorkManger");
            mNotificationManager.createNotificationChannel(channel);
        }
        NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(getApplicationContext(), "1")
                .setSmallIcon(R.mipmap.ic_launcher) // notification icon
                .setContentTitle(title) // title for notification
                .setContentText(message)// message for notification
                .setAutoCancel(true); // clear notification after click
        Intent intent = new Intent(getApplicationContext(), MainActivity.class);
        PendingIntent pi = PendingIntent.getActivity(getApplicationContext(), 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
        mBuilder.setContentIntent(pi);
        mNotificationManager.notify(0, mBuilder.build());
    }
}

 

activity_main.xml :

Just a simple view with a textview because this project is completely background task and output is shown through push notification

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout 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:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Hello World!"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toTopOf="parent" />

</androidx.constraintlayout.widget.ConstraintLayout>

 

MainActivity.class

We will make declarations for making android work manager periodic work request

Kotlin :

kotlin code for periodic work request

import android.os.Bundle
import android.util.Log
import androidx.appcompat.app.AppCompatActivity
import androidx.work.*
import java.util.concurrent.TimeUnit

class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        val constraints = Constraints.Builder().setRequiresCharging(true)
            .setRequiredNetworkType(NetworkType.UNMETERED).build()


        val periodicWorkRequest =
            PeriodicWorkRequest.Builder(BackgroundTask::class.java, 1, TimeUnit.SECONDS)
                .setInputData(Data.Builder().putBoolean("isStart", true).build())
                .setInitialDelay(6000, TimeUnit.MILLISECONDS)
                .build()

        val workManager = WorkManager.getInstance(this)

        workManager.enqueue(periodicWorkRequest)

        workManager.getWorkInfoByIdLiveData(periodicWorkRequest.id).observeForever {
            if (it != null) {

                Log.d("periodicWorkRequest", "Status changed to ${it.state.isFinished}")

            }
        }

    }

}

 

Java :

java code for the periodic work request

import android.os.Bundle;
import android.util.Log;

import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
import androidx.lifecycle.Observer;
import androidx.work.Constraints;
import androidx.work.NetworkType;
import androidx.work.PeriodicWorkRequest;
import androidx.work.WorkInfo;
import androidx.work.WorkManager;

import java.util.concurrent.TimeUnit;

public class MainActivityJava extends AppCompatActivity {
    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        Constraints constraints = new Constraints.Builder().setRequiresCharging(true).setRequiredNetworkType(NetworkType.UNMETERED).build();

        final PeriodicWorkRequest periodicWorkRequest1 = new PeriodicWorkRequest.Builder(BackgroundTaskJava.class,1, TimeUnit.MILLISECONDS)
                .setInitialDelay(6000,TimeUnit.MILLISECONDS)
                .build();

        WorkManager workManager =  WorkManager.getInstance(this);

        workManager.enqueue(periodicWorkRequest1);

        workManager.getWorkInfoByIdLiveData(periodicWorkRequest1.getId())
                .observe(this, new Observer<WorkInfo>() {
                    @Override
                    public void onChanged(@Nullable WorkInfo workInfo) {
                        if (workInfo != null) {
                            Log.d("periodicWorkRequest", "Status changed to : " + workInfo.getState());

                        }
                    }
                });
    }
}

 

 

 

Output :

Finally we can see the notification popped up when the alarm goes off using android work manager.

 

android work manager

 

If you have any query on android work manager do let us know in the comment section below.If you like this tutorial do like share for more interesting updates.

 

Show Buttons
Hide Buttons
Read previous post:
Kotlin Synthetic Binding || A new way to bind UI components

  Kotlin Synthetic Binding : Kotlin synthetic binding makes it much simpler and easier to bind views in your code....

Close