Fix widget/app showing stale or no data; add live in-app refresh
Three reliability bugs made data inconsistent: 1. Empty-overwrite: a failed or partial fetch returned an empty UsageData that the worker/app saved unconditionally, wiping the last good reading and blanking the widget. Added UsageData.mergedWith() so a fetch that returns nothing usable keeps the previous snapshot, and a partial fetch falls back per-metric. Never blank again. 2. No in-app auto-refresh: onResume only refreshed when the cache was >5 min old and there was no live timer. Replaced with a foreground lifecycle loop that refreshes on open and every 30s while visible, always painting cached data first. Manual button keeps the spinner; the loop is silent. App refresh now also pushes the widget update. 3. Spurious logout: a single transient 401/403 (e.g. a Cloudflare challenge) called clearSession() immediately, logging the user out and showing "Not signed in". Now clears only after 3 consecutive auth failures; the counter resets on any successful read. Battery-friendly: no foreground service. Background widget refresh stays on the existing alarm + 15-min WorkManager, but with the merge fix the widget always shows the last data it pulled. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -74,6 +74,18 @@ class PreferencesManager(context: Context) {
|
||||
|
||||
fun isLoggedIn(): Boolean = !getCookies().isNullOrBlank()
|
||||
|
||||
// Consecutive 401/403 counter — we only clear the session after several in a row, so a
|
||||
// single transient auth failure (e.g. a Cloudflare challenge) doesn't log the user out.
|
||||
fun getAuthFailCount(): Int = prefs.getInt(KEY_AUTH_FAILS, 0)
|
||||
fun incAuthFailCount(): Int {
|
||||
val n = getAuthFailCount() + 1
|
||||
prefs.edit().putInt(KEY_AUTH_FAILS, n).apply()
|
||||
return n
|
||||
}
|
||||
fun resetAuthFailCount() {
|
||||
if (getAuthFailCount() != 0) prefs.edit().putInt(KEY_AUTH_FAILS, 0).apply()
|
||||
}
|
||||
|
||||
// ── Usage history (for the in-app chart) ─────────────────────────────────
|
||||
|
||||
/**
|
||||
@@ -140,6 +152,7 @@ class PreferencesManager(context: Context) {
|
||||
private const val KEY_NOTIFY_ENABLED = "notify_enabled"
|
||||
private const val KEY_NOTIFY_SESSION_PCT = "notify_session_pct"
|
||||
private const val KEY_NOTIFY_WEEKLY_PCT = "notify_weekly_pct"
|
||||
private const val KEY_AUTH_FAILS = "auth_fail_count"
|
||||
|
||||
private const val MIN_HISTORY_GAP_MS = 2 * 60 * 1000L // collapse readings <2 min apart
|
||||
private const val HISTORY_RETENTION_MS = 7 * 24 * 60 * 60 * 1000L // keep 7 days
|
||||
|
||||
Reference in New Issue
Block a user