From 4357abbff4533a1b78fb2539769668498c1e9d1c Mon Sep 17 00:00:00 2001 From: 2dust <31833384+2dust@users.noreply.github.com> Date: Thu, 10 Jul 2025 20:11:34 +0800 Subject: [PATCH] Bug fix https://github.com/2dust/v2rayNG/issues/4723 --- .../com/v2ray/ang/service/V2RayVpnService.kt | 65 +++++++++++++------ 1 file changed, 46 insertions(+), 19 deletions(-) diff --git a/V2rayNG/app/src/main/java/com/v2ray/ang/service/V2RayVpnService.kt b/V2rayNG/app/src/main/java/com/v2ray/ang/service/V2RayVpnService.kt index d734c299..79ee528b 100644 --- a/V2rayNG/app/src/main/java/com/v2ray/ang/service/V2RayVpnService.kt +++ b/V2rayNG/app/src/main/java/com/v2ray/ang/service/V2RayVpnService.kt @@ -194,25 +194,7 @@ class V2RayVpnService : VpnService(), ServiceControl { builder.setSession(V2RayServiceManager.getRunningServerName()) - val selfPackageName = BuildConfig.APPLICATION_ID - if (MmkvManager.decodeSettingsBool(AppConfig.PREF_PER_APP_PROXY)) { - val apps = MmkvManager.decodeSettingsStringSet(AppConfig.PREF_PER_APP_PROXY_SET) - val bypassApps = MmkvManager.decodeSettingsBool(AppConfig.PREF_BYPASS_APPS) - //process self package - if (bypassApps) apps?.add(selfPackageName) else apps?.remove(selfPackageName) - apps?.forEach { - try { - if (bypassApps) - builder.addDisallowedApplication(it) - else - builder.addAllowedApplication(it) - } catch (e: PackageManager.NameNotFoundException) { - Log.e(AppConfig.TAG, "Failed to configure app in VPN: ${e.localizedMessage}", e) - } - } - } else { - builder.addDisallowedApplication(selfPackageName) - } + configurePerAppProxy(builder) // Close the old interface since the parameters have been changed. try { @@ -249,6 +231,51 @@ class V2RayVpnService : VpnService(), ServiceControl { return false } + /** + * Configures per-app proxy rules for the VPN builder. + * + * - If per-app proxy is not enabled, disallow the VPN service's own package. + * - If no apps are selected, disallow the VPN service's own package. + * - If bypass mode is enabled, disallow all selected apps (including self). + * - If proxy mode is enabled, only allow the selected apps (excluding self). + * + * @param builder The VPN Builder to configure. + */ + private fun configurePerAppProxy(builder: Builder) { + val selfPackageName = BuildConfig.APPLICATION_ID + + // If per-app proxy is not enabled, disallow the VPN service's own package and return + if (MmkvManager.decodeSettingsBool(AppConfig.PREF_PER_APP_PROXY) == false) { + builder.addDisallowedApplication(selfPackageName) + return + } + + // If no apps are selected, disallow the VPN service's own package and return + val apps = MmkvManager.decodeSettingsStringSet(AppConfig.PREF_PER_APP_PROXY_SET) + if (apps.isNullOrEmpty()) { + builder.addDisallowedApplication(selfPackageName) + return + } + + val bypassApps = MmkvManager.decodeSettingsBool(AppConfig.PREF_BYPASS_APPS) + // Handle the VPN service's own package according to the mode + if (bypassApps) apps.add(selfPackageName) else apps.remove(selfPackageName) + + apps.forEach { + try { + if (bypassApps) { + // In bypass mode, disallow the selected apps + builder.addDisallowedApplication(it) + } else { + // In proxy mode, only allow the selected apps + builder.addAllowedApplication(it) + } + } catch (e: PackageManager.NameNotFoundException) { + Log.e(AppConfig.TAG, "Failed to configure app in VPN: ${e.localizedMessage}", e) + } + } + } + /** * Runs the tun2socks process. * Starts the tun2socks process with the appropriate parameters.