Workout your tasks with WorkManager — Basics
Tags: workmanager, architecture, androiddev, androidjetpack
Published: 2020-06-27 13:57:55

---
title: Workout your tasks with WorkManager — Basics
published: true
date: 2019-07-04 18:46:50 UTC
tags: workmanager,architecture,androiddev,androidjetpack
canonical_url: https://proandroiddev.com/workout-your-tasks-with-workmanager-main-components-1c0c66317a3e
---

### Workout your tasks with WorkManager — Main Components

![](https://cdn-images-1.medium.com/max/960/1*gOqQSVM9Ictd7d9T85Yl-A.png)

_“WorkManager is a library for managing_ **_deferrable_** _and_ **_guaranteed_** _background work.”_

In my [previous post](https://medium.com/@magdamiu/workout-your-tasks-with-workmanager-intro-db5aefe14d66) I covered details about the Android memory model, battery optimization features, current background processing solutions and what are the main advantages of [WorkManage](https://developer.android.com/topic/libraries/architecture/workmanager) and where it should be used.

In this blog post I’ll cover the main components of WorkManager library:

- Worker
- WorkRequest
- Constraints
- Input/Output Data
- WorkManager

In order to use WorkManager in our app first of all we should declare the **dependencies** :

- Open the build.gradle file of the **project** and add the google() repository as shown below:

{% gist https://gist.github.com/magdamiu/1c8e63216e2c495f50c3b5fefc81ff24 %}

- Open the build.gradle file of the **module (app)** and add necessary dependencies as shown below:

{% gist https://gist.github.com/magdamiu/381dc48c83efe776c3bbb54a99b6e3ec %}

The main components of WorkManager are:

- [Worker](https://developer.android.com/reference/androidx/work/Worker)
- [WorkRequest](https://developer.android.com/reference/androidx/work/WorkRequest)
- [WorkManager](https://developer.android.com/reference/androidx/work/WorkManager)

So first of all we need to create a background task by extending the _Worker_ class. After that we configure how and when to run the task by using the _WorkRequest_ implementations and finally we hand off the task to the system.

Q: What happens behind the scenes? What is the internal mechanism used by worked manager?

A: Actually, WorkManager is more like a wrapper on the existing background processing solutions for deferrable and guaranteed work.

![](https://cdn-images-1.medium.com/max/960/1*QbCxv1srHGcw6diIXtDGaw.png)

### 1️⃣Worker

A task is defined by the Worker class. The function _doWork()_ runs synchronously on a background thread.

![](https://cdn-images-1.medium.com/max/960/1*XHGKkIt0n0Hu_CJGSjkctg.png)<figcaption>Worker implementation</figcaption>

{% gist https://gist.github.com/magdamiu/5facbfde93857b2edbca319448d2fa88 %}

### 2️⃣WorkRequest

When a task is defined we should specify it is a periodic one or not. If it is periodic we will use _PeriodicWorkRequest_ class, if not we will use _OneTimeWorkRequest_.

**_OneTimeWorkRequest_**

- It is used for non-repeating work
- It could have an initial delay
- It could be part of a chain or graph of work

**_PeriodicWorkRequest_**

- Used for tasks that need to execute periodically
- The minimum repeat interval that can be defined is 15 minutes (same as the _JobScheduler_ API) and it cannot have an initial delay
- It cannot be part of a chain or graph of work
- Before v2.1-alpha02 it’s not possible to create a PeriodicWorkRequest with an initial delay.
- The execution may be delayed because _WorkManager_ is subject to OS battery optimizations, such as doze mode

![](https://cdn-images-1.medium.com/max/960/1*bIoUSTZ6lIeRA35QqLshUw.png)

{% gist https://gist.github.com/magdamiu/6b3ab19efe93c9591ae6d07d1545de23 %}

![](https://cdn-images-1.medium.com/max/960/1*BqGqJ6m7g4rdbc1lCp2yXA.png)

![](https://cdn-images-1.medium.com/max/960/1*VhraYsB_G2tgwUyUBop54w.png)

![](https://cdn-images-1.medium.com/max/960/1*b81YL-mD3QjWNqWQzve56A.png)<figcaption>Happy and Unhappy paths for One Time Work and Periodic Work</figcaption>

Let’s say that our task should run only when some conditions are met, maybe we need a wi-fi connection and the device should be idle. This thing is possible in WorkManager by using the _Constraints_ class and there 5 limitations that could be used:

- network type limitations: _setRequiredNetworkType(requiredNetworkType: NetworkType)_
- battery level limitations: _setRequiresBatteryNotLow(requiresBatteryNotLow: Boolean)_
- charging limitations: _setRequiresCharging(requiresCharging: Boolean)_
- status of the device limitations: _setRequiresDeviceIdle(requiresDeviceIdle: Boolean)_
- storage level limitations: _setRequiresStorageNotLow(requiresStorageNotLow: Boolean)_

Related to the _NetworkType_ options, the enum have 5 values:

- CONNECTED — Any working network connection
- METERED — A metered network connection
- NOT\_REQUIRED — A network is not required for this work.
- NOT\_ROAMING — A non-roaming network connection
- UNMETERED — An unmetered network connection

We can apply the constraints like this:

{% gist https://gist.github.com/magdamiu/51b01ef9e2a3993e56819daa765c902a %}

Input and output Data

- The _Data.Builder_ helper class lets us to provide data to our Worker.
- Please keep in mind that this should not exceed 10KB. We will get an _IllegalStateException_ if we pass data that exceeds this limit.
- Think of _Data_ as a key-value pairs store, not unlike _SharedPreferences_.

![](https://cdn-images-1.medium.com/max/960/1*8Me1KGAiVwaJZOTl3ndz0A.png)

{% gist https://gist.github.com/magdamiu/497d032696ca2f2e75fc94a236cdeeec %}

### 3️⃣WorkManager

After the work was defined by the _Worker_ class and we know also the type of the task (periodic or not) we can now schedule it with [WorkManager](https://developer.android.com/reference/androidx/work/WorkManager) using the [enqueue()](https://developer.android.com/reference/androidx/work/WorkManager.html#enqueue(androidx.work.WorkRequest)) method.

And if we decide to cancel all the work we could use the [cancelAllWork()](https://developer.android.com/reference/androidx/work/WorkManager.html#cancelAllWork()) method.

![](https://cdn-images-1.medium.com/max/960/1*ua-nWKS0XCISZQrG4355lg.png)<figcaption>WorkManager methods</figcaption>

{% gist https://gist.github.com/magdamiu/5129d4d9d8d8702b3bf1f9dc2b33eecc %}

An important thing to mention on how to retrieve the _WorkManager_ instance:

> _WorkManager v2.1 has deprecated_ [WorkManager#getInstance()](https://developer.android.com/reference/androidx/work/WorkManager.html#getInstance()) _and there’s now a new_ [WorkManager#getInstance(context: Context)](https://developer.android.com/reference/androidx/work/WorkManager.html#getInstance(android.content.Context)) _that works in the same way but supports the new_ [_on-demand initialization_](https://developer.android.com/topic/libraries/architecture/workmanager/advanced/custom-configuration#on-demand)_. In this article I’m going to use this new syntax that expects that we pass a context to retrieve the WorkManager instance._

In the next article, we’ll take a closer look on features like _BackoffPolicy_, how to identify a task, how to get the status of a task, how to combine the tasks and the graphs of tasks (chaining the work) and how to merge the inputs and outputs. Stay tuned!

That’s it for now, hope it helps! Enjoy and feel free to leave a comment if something is not clear or if you have questions. Thank you for reading! 🙌🙏😍✌

* * *