Fix update notification: add banner UI + reset rate limit on version change

This commit is contained in:
ngenohkevin
2026-03-21 22:35:00 +03:00
parent d29498edbb
commit 00975aa7cc
3 changed files with 54 additions and 3 deletions
@@ -38,6 +38,7 @@ import com.ledga.app.ui.components.TransactionCard
import com.ledga.app.ui.components.categoryIcon
import com.ledga.app.ui.components.parseColor
import com.ledga.app.ui.theme.MpesaGreen
import com.ledga.app.ui.theme.MpesaGreenDark
import com.ledga.app.util.CurrencyFormatter
@Composable
@@ -52,9 +53,46 @@ fun HomeScreen(
.padding(horizontal = 16.dp),
verticalArrangement = Arrangement.spacedBy(16.dp)
) {
// Update banner
if (state.updateAvailable != null) {
item {
Spacer(modifier = Modifier.height(12.dp))
Card(
modifier = Modifier.fillMaxWidth(),
shape = RoundedCornerShape(16.dp),
colors = CardDefaults.cardColors(
containerColor = MpesaGreenDark
)
) {
Row(
modifier = Modifier
.fillMaxWidth()
.padding(16.dp),
verticalAlignment = Alignment.CenterVertically
) {
Column(modifier = Modifier.weight(1f)) {
Text(
text = "Update Available",
style = MaterialTheme.typography.titleSmall,
fontWeight = FontWeight.Bold,
color = androidx.compose.ui.graphics.Color.White
)
Text(
text = "Version ${state.updateAvailable!!.tag_name}",
style = MaterialTheme.typography.bodySmall,
color = androidx.compose.ui.graphics.Color.White.copy(alpha = 0.8f)
)
}
}
}
}
}
// Greeting
item {
Spacer(modifier = Modifier.height(12.dp))
if (state.updateAvailable == null) {
Spacer(modifier = Modifier.height(12.dp))
}
Text(
text = state.greeting,
style = MaterialTheme.typography.headlineMedium,
@@ -128,6 +128,8 @@ class HomeViewModel @Inject constructor(
donutSegments = segments,
categoryBreakdown = breakdown
)
}.combine(_updateAvailable) { state, update ->
state.copy(updateAvailable = update)
}.stateIn(viewModelScope, SharingStarted.WhileSubscribed(5000), HomeUiState())
fun selectPeriod(period: Period) {
@@ -47,6 +47,7 @@ object UpdateChecker {
private val json = Json { ignoreUnknownKeys = true }
private const val PREFS_NAME = "update_prefs"
private const val LAST_CHECK_KEY = "last_check"
private const val LAST_VERSION_KEY = "last_version"
suspend fun checkForUpdate(
context: Context,
@@ -54,11 +55,21 @@ object UpdateChecker {
repo: String,
currentVersion: String
): GitHubRelease? = withContext(Dispatchers.IO) {
// Rate limit: max once per day
val prefs = context.getSharedPreferences(PREFS_NAME, Context.MODE_PRIVATE)
val lastCheck = prefs.getLong(LAST_CHECK_KEY, 0)
val lastVersion = prefs.getString(LAST_VERSION_KEY, "") ?: ""
val oneDayMs = 24 * 60 * 60 * 1000L
if (System.currentTimeMillis() - lastCheck < oneDayMs) return@withContext null
// Reset rate limit if app version changed (just updated)
val versionChanged = lastVersion != currentVersion
if (versionChanged) {
prefs.edit().putString(LAST_VERSION_KEY, currentVersion).apply()
}
// Rate limit: max once per day (skip if version just changed)
if (!versionChanged && System.currentTimeMillis() - lastCheck < oneDayMs) {
return@withContext null
}
prefs.edit().putLong(LAST_CHECK_KEY, System.currentTimeMillis()).apply()