Permissions & Background Work
Runtime permissions
Dangerous permissions (camera, location, contacts) must be requested at runtime, not just in the manifest.
val launcher = registerForActivityResult(
ActivityResultContracts.RequestPermission()
) { granted ->
if (granted) openCamera() else showMessage("Permission needed")
}
launcher.launch(Manifest.permission.CAMERA)
Background work with WorkManager
For tasks that must run even if the app closes (sync, upload), use WorkManager.
class SyncWorker(ctx: Context, params: WorkerParameters) : CoroutineWorker(ctx, params) {
override suspend fun doWork(): Result {
// do the sync...
return Result.success()
}
}
val work = OneTimeWorkRequestBuilder<SyncWorker>().build()
WorkManager.getInstance(this).enqueue(work)
Choose the right tool: short async work → coroutines; guaranteed deferred work → WorkManager; long foreground task (music) → a Foreground Service.