fix(core,android): stop suspending the Core in Doze

The suspended tunnel rejected the traffic Doze still lets through, which
kept FCM from reconnecting, and the re-probe on resume tested every node,
select groups included.

Changelog: Push notifications reconnect in Doze
This commit is contained in:
chen08209
2026-09-27 16:39:11 +08:00
parent e131675bdf
commit 1e9955dec6
9 changed files with 56 additions and 243 deletions
-7
View File
@@ -68,13 +68,6 @@ Java_com_follow_clash_core_Core_getTotalTraffic(JNIEnv *env, jobject thiz,
return new_string(traffic);
}
extern "C"
JNIEXPORT void JNICALL
Java_com_follow_clash_core_Core_suspended(JNIEnv *env, jobject thiz, jboolean suspended,
jboolean interactive) {
suspend(suspended, interactive);
}
extern "C"
JNIEXPORT void JNICALL
Java_com_follow_clash_core_Core_quickSetup(JNIEnv *env, jobject thiz, jstring init_params_string,
@@ -60,11 +60,6 @@ object Core {
)
}
external fun suspended(
suspended: Boolean,
interactive: Boolean,
)
private external fun invokeMethod(
data: String,
cb: InvokeInterface,
@@ -24,7 +24,6 @@ internal class ServiceModules(private val service: Service) {
val nextModules = listOf(
NotificationModule(service, nextScope),
NetworkObserveModule(service),
SuspendModule(service, nextScope),
)
val startedModules = mutableListOf<ServiceModule>()
@@ -1,47 +0,0 @@
package com.follow.clash.service.modules
import android.app.Service
import android.content.Intent
import android.os.PowerManager
import androidx.core.content.getSystemService
import com.follow.clash.common.receiveBroadcastFlow
import com.follow.clash.core.Core
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.flow.map
import kotlinx.coroutines.flow.onStart
import kotlinx.coroutines.launch
internal class SuspendModule(
private val service: Service,
private val scope: CoroutineScope,
) : ServiceModule {
private fun isScreenOn() =
service.getSystemService<PowerManager>()?.isInteractive ?: true
private val isDeviceIdle: Boolean
get() = service.getSystemService<PowerManager>()?.isDeviceIdleMode ?: true
private fun updateSuspension(screenOn: Boolean) {
Core.suspended(!screenOn && isDeviceIdle, screenOn)
}
override fun start() {
scope.launch {
val screenFlow = service.receiveBroadcastFlow {
addAction(Intent.ACTION_SCREEN_ON)
addAction(Intent.ACTION_SCREEN_OFF)
addAction(PowerManager.ACTION_DEVICE_IDLE_MODE_CHANGED)
}.map {
isScreenOn()
}.onStart {
emit(isScreenOn())
}
screenFlow.collect(::updateSuspension)
}
}
override fun stop() {
Core.suspended(false, isScreenOn())
}
}