DataControl v0.1.0 : contrôle du forfait data mobile via pare-feu VPN local

Surveillance de la consommation de données mobiles avec coupure automatique
en cas de dépassement de forfait, sans root ni impact sur le Wi-Fi.

- Pare-feu local (VpnService) actif uniquement sur données mobiles
- Liste blanche d'applications toujours autorisées
- Coupure cyclique totale après dépassement (intervalle paramétrable)
- Réglages complets (forfait, prix, date de début, reset auto/manuel)
- Estimation du coût total en temps réel
- Notification permanente colorée par état
- UI Compose Material 3

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
JohnnyandClaude Sonnet 5 committed 2026-07-02 18:37:45 +02:00
1 parent a71026898b
commit 536a981f9e
57 files changed
+2871

No files matched your search

@@ -0,0 +1,39 @@
package com.jttools.datacontrol.service
import android.content.BroadcastReceiver
import android.content.Context
import android.content.Intent
import com.jttools.datacontrol.data.SettingsRepository
import dagger.hilt.android.AndroidEntryPoint
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import kotlinx.coroutines.flow.first
import dagger.hilt.android.EntryPointAccessors
import dagger.hilt.InstallIn
import dagger.hilt.components.SingletonComponent
import dagger.hilt.EntryPoint
class BootReceiver : BroadcastReceiver() {
@EntryPoint
@InstallIn(SingletonComponent::class)
interface BootReceiverEntryPoint {
fun settingsRepository(): SettingsRepository
}
override fun onReceive(context: Context, intent: Intent?) {
if (intent?.action != Intent.ACTION_BOOT_COMPLETED) return
val appContext = context.applicationContext
val entryPoint = EntryPointAccessors.fromApplication(appContext, BootReceiverEntryPoint::class.java)
val pendingResult = goAsync()
CoroutineScope(Dispatchers.Default).launch {
try {
val enabled = entryPoint.settingsRepository().settingsFlow.first().controlEnabled
if (enabled) DataMonitorService.start(appContext)
} finally {
pendingResult.finish()
}
}
}
}