package com.dmc.callcrm.service import android.app.Notification import android.app.Service import android.content.Context import android.content.Intent import android.os.Build import android.os.IBinder import androidx.core.app.NotificationCompat import com.dmc.callcrm.App import com.dmc.callcrm.R import com.dmc.callcrm.sync.Syncer import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.SupervisorJob import kotlinx.coroutines.cancel import kotlinx.coroutines.launch /** * A lightweight foreground service. It exists mainly to give the app a * persistent, OS-visible reason to run so a sync can fire right after a call, * even when the app UI is closed. Actual periodic work is done by WorkManager. */ class CallMonitorService : Service() { private val scope = CoroutineScope(SupervisorJob() + Dispatchers.IO) override fun onCreate() { super.onCreate() startForeground(NOTIF_ID, buildNotification()) } override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int { scope.launch { Syncer.run(applicationContext) } return START_STICKY // restart if the OS kills us } private fun buildNotification(): Notification = NotificationCompat.Builder(this, App.CHANNEL_ID) .setContentTitle(getString(R.string.notif_title)) .setContentText(getString(R.string.notif_text)) .setSmallIcon(android.R.drawable.stat_sys_upload) .setOngoing(true) .setPriority(NotificationCompat.PRIORITY_LOW) .build() override fun onDestroy() { scope.cancel() super.onDestroy() } override fun onBind(intent: Intent?): IBinder? = null companion object { private const val NOTIF_ID = 1001 fun start(ctx: Context) { val i = Intent(ctx, CallMonitorService::class.java) if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { ctx.startForegroundService(i) } else { ctx.startService(i) } } } }