Skip to main content
Version: 4.2 - LTS

WorkManager

Koin integrates with Android WorkManager to enable constructor injection in Workers.

Setup​

Add Dependencies​

implementation "io.insert-koin:koin-android:$koin_version"
implementation "io.insert-koin:koin-androidx-workmanager:$koin_version"

Configure WorkManager​

Set up the Koin WorkManager factory in your Application:

class MainApplication : Application() {

override fun onCreate() {
super.onCreate()

startKoin {
androidContext(this@MainApplication)
workManagerFactory()
modules(appModule)
}
}
}

Disable Default Initializer​

Add to your AndroidManifest.xml to disable the default WorkManager initializer:

<provider
android:name="androidx.startup.InitializationProvider"
android:authorities="${applicationId}.androidx-startup"
android:exported="false"
tools:node="merge">
<meta-data
android:name="androidx.work.WorkManagerInitializer"
android:value="androidx.startup"
tools:node="remove" />
</provider>

Declaring Workers​

Compiler Plugin DSL​

class MyWorker(
context: Context,
workerParams: WorkerParameters,
private val myService: MyService
) : CoroutineWorker(context, workerParams) {

override suspend fun doWork(): Result {
myService.performTask()
return Result.success()
}
}

val appModule = module {
single<MyService>()
worker<MyWorker>()
}

Annotations​

@KoinWorker
class MyWorker(
context: Context,
workerParams: WorkerParameters,
private val myService: MyService
) : CoroutineWorker(context, workerParams) {

override suspend fun doWork(): Result {
myService.performTask()
return Result.success()
}
}

@Singleton
class MyService

Classic DSL​

val appModule = module {
single { MyService() }
worker { params ->
MyWorker(
context = params.get(),
workerParams = params.get(),
myService = get()
)
}
}

Enqueuing Work​

Use WorkManager normally to enqueue your worker:

val workRequest = OneTimeWorkRequestBuilder<MyWorker>().build()
WorkManager.getInstance(context).enqueue(workRequest)

Worker with Parameters​

Pass parameters via WorkManager's input data:

@KoinWorker
class SyncWorker(
context: Context,
workerParams: WorkerParameters,
private val repository: DataRepository
) : CoroutineWorker(context, workerParams) {

override suspend fun doWork(): Result {
val userId = inputData.getString("USER_ID") ?: return Result.failure()
repository.syncUser(userId)
return Result.success()
}
}

Enqueue with data:

val workRequest = OneTimeWorkRequestBuilder<SyncWorker>()
.setInputData(workDataOf("USER_ID" to "123"))
.build()

WorkManager.getInstance(context).enqueue(workRequest)

Quick Reference​

ApproachDeclaration
Compiler Plugin DSLworker<MyWorker>()
Annotations@KoinWorker
Classic DSLworker { params -> MyWorker(params.get(), params.get(), get()) }
SetupCode
Enable factoryworkManagerFactory() in startKoin
Disable defaultRemove WorkManagerInitializer in manifest

Next Steps​