Skip to content

Auto update impr#327

Merged
rainxchzed merged 6 commits intomainfrom
auto-update-impr
Mar 14, 2026
Merged

Auto update impr#327
rainxchzed merged 6 commits intomainfrom
auto-update-impr

Conversation

@rainxchzed
Copy link
Member

@rainxchzed rainxchzed commented Mar 14, 2026

Add UpdateScheduleManager and its Android and Desktop implementations

Summary by CodeRabbit

  • New Features

    • App now self-registers as an installed application on first launch.
    • Configurable background update-check interval (3h, 6h, 12h, 24h) with persistent preference (default 6h) and UI to change it in Profile.
  • Platform

    • Interval changes take effect immediately; background scheduling active on mobile and is a no-op on desktop.
  • Localization

    • Added update-related strings across multiple locales.

- Add `OnUpdateCheckIntervalChanged` action and update `ProfileState` to include `updateCheckIntervalHours`.
- Implement `getUpdateCheckInterval` and `setUpdateCheckInterval` in `ThemesRepository`.
- Add `UpdateScheduleManager` interface with platform-specific implementations to handle rescheduling of background tasks.
- Implement `reschedule` logic in `UpdateScheduler` (Android) using WorkManager with `ExistingPeriodicWorkPolicy.UPDATE`.
- Add a new "Updates" section to the Profile screen with a selection card for intervals (3h, 6h, 12h, 24h).
- Register `UpdateScheduleManager` in Android and JVM dependency injection modules.
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Mar 14, 2026

Caution

Review failed

Pull request was closed or merged during review

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: b50f489a-90ca-4dc9-b4af-6e54bdaf5503

📥 Commits

Reviewing files that changed from the base of the PR and between 82b1971 and b23d815.

📒 Files selected for processing (1)
  • composeApp/src/androidMain/kotlin/zed/rainxch/githubstore/app/GithubStoreApp.kt

Walkthrough

Adds a cross-platform UpdateScheduleManager, storage and UI for update-check interval, WorkManager reschedule API, platform DI bindings, Android app self-registration as an InstalledApp, and background rescheduling at startup and on interval changes.

Changes

Cohort / File(s) Summary
App init & self-registration
composeApp/src/androidMain/kotlin/.../GithubStoreApp.kt
Adds appScope (SupervisorJob+IO), calls registerSelfAsInstalledApp() on startup, reads interval from ThemesRepository, and launches scheduling using UpdateScheduleManager via a safe coroutine.
Scheduling abstraction & platform bindings
core/domain/src/commonMain/kotlin/.../UpdateScheduleManager.kt, core/data/src/androidMain/kotlin/.../AndroidUpdateScheduleManager.kt, core/data/src/jvmMain/kotlin/.../DesktopUpdateScheduleManager.kt, core/data/src/.../di/PlatformModule.android.kt, core/data/src/.../di/PlatformModule.jvm.kt
Adds UpdateScheduleManager interface, Android implementation delegating to UpdateScheduler, a no-op Desktop implementation, and DI singletons for each platform.
WorkManager reschedule API
core/data/src/androidMain/kotlin/.../UpdateScheduler.kt
Adds UpdateScheduler.reschedule(context, intervalHours) to replace existing periodic work using ExistingPeriodicWorkPolicy.UPDATE and exponential backoff.
Interval persistence in ThemesRepository
core/data/src/commonMain/kotlin/.../ThemesRepositoryImpl.kt, core/domain/src/commonMain/kotlin/.../ThemesRepository.kt
Adds DataStore key and default (6L), getUpdateCheckInterval(): Flow<Long> and setUpdateCheckInterval(hours: Long) to persist/read update interval; exposes methods in repository interface.
Profile feature — state, actions, viewmodel
feature/profile/presentation/src/commonMain/kotlin/.../ProfileState.kt, .../ProfileAction.kt, .../ProfileViewModel.kt
Adds updateCheckIntervalHours to state, OnUpdateCheckIntervalChanged(hours) action, loads stored interval on startup, and calls UpdateScheduleManager.reschedule when interval changes.
Profile UI & components
feature/profile/presentation/src/commonMain/kotlin/.../ProfileRoot.kt, feature/profile/presentation/src/commonMain/kotlin/.../components/sections/Installation.kt
Inserts updatesSection into profile UI and adds UpdateCheckIntervalCard composable with selectable FilterChips for 3h/6h/12h/24h emitting the interval change action.
Localization / strings
core/presentation/src/commonMain/composeResources/values*/strings-*.xml
Adds update-related strings across many locales: section_updates, update_check_interval_title, update_check_interval_description, interval_3h, interval_6h, interval_12h, interval_24h.
Build / deps
composeApp/build.gradle.kts
Adds libs.touchlab.kermit dependency to commonMain.

Sequence Diagram(s)

sequenceDiagram
    participant User
    participant UI
    participant VM
    participant Repo as ThemesRepository
    participant Manager as UpdateScheduleManager
    participant Scheduler as UpdateScheduler
    participant WM as WorkManager

    User->>UI: Select interval (e.g. 6h)
    UI->>VM: OnUpdateCheckIntervalChanged(6)
    VM->>Repo: setUpdateCheckInterval(6)
    Repo-->>VM: persisted
    VM->>Manager: reschedule(6)
    Manager->>Scheduler: reschedule(context, 6)
    Scheduler->>WM: enqueue PeriodicWorkRequest(interval=6h, UPDATE)
    WM-->>Scheduler: scheduled
    Scheduler-->>Manager: done
    Manager-->>VM: done
    VM-->>UI: state.updateCheckIntervalHours = 6
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Possibly related PRs

Poem

🐰 I hopped through code with nimble paws,

I set the clocks and tuned the cause.
Three, six, twelve, or twenty-four —
Background checks that hum once more.
The app found itself; I thumped applause!

🚥 Pre-merge checks | ✅ 1 | ❌ 2

❌ Failed checks (1 warning, 1 inconclusive)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 6.90% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
Title check ❓ Inconclusive The title 'Auto update impr' is vague and does not clearly summarize the main changes, using a non-descriptive abbreviation 'impr' that doesn't convey meaningful information about the changeset. Use a more descriptive title such as 'Add configurable update check intervals' or 'Implement update schedule manager with interval configuration' to clearly communicate the primary change.
✅ Passed checks (1 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
  • 📝 Generate docstrings (stacked PR)
  • 📝 Generate docstrings (commit on current branch)
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch auto-update-impr
📝 Coding Plan
  • Generate coding plan for human review comments

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🧹 Nitpick comments (4)
core/data/src/commonMain/kotlin/zed/rainxch/core/data/repository/ThemesRepositoryImpl.kt (1)

118-122: Consider validating the hours parameter.

The setter accepts any Long value, including zero or negative values, which would result in invalid scheduling behavior. Consider adding validation to ensure the interval is within acceptable bounds.

💡 Optional fix to add validation
 override suspend fun setUpdateCheckInterval(hours: Long) {
+    require(hours > 0) { "Update check interval must be positive" }
     preferences.edit { prefs ->
         prefs[UPDATE_CHECK_INTERVAL_KEY] = hours
     }
 }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@core/data/src/commonMain/kotlin/zed/rainxch/core/data/repository/ThemesRepositoryImpl.kt`
around lines 118 - 122, The setter setUpdateCheckInterval currently writes any
Long into UPDATE_CHECK_INTERVAL_KEY via preferences.edit without validation;
update it to validate the hours parameter (e.g., require hours > 0 and
optionally enforce an upper bound) before writing to preferences—either throw an
IllegalArgumentException for invalid values or clamp to a safe range—and
document the behavior so callers of setUpdateCheckInterval know invalid inputs
are rejected or normalized.
feature/profile/presentation/src/commonMain/kotlin/zed/rainxch/profile/presentation/components/sections/Installation.kt (2)

431-434: Avoid re-dispatch on already-selected interval.

Guard the chip click to no-op when the current option is already selected, so you avoid redundant repository writes and scheduler calls.

Small click-guard improvement
                     FilterChip(
                         selected = isSelected,
-                        onClick = { onIntervalSelected(hours) },
+                        onClick = {
+                            if (!isSelected) onIntervalSelected(hours)
+                        },
                         label = {
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@feature/profile/presentation/src/commonMain/kotlin/zed/rainxch/profile/presentation/components/sections/Installation.kt`
around lines 431 - 434, The FilterChip onClick currently always calls
onIntervalSelected(hours) even when the option is already selected; change the
onClick handler inside the FilterChip component to first check isSelected and
return/do nothing if true, otherwise call onIntervalSelected(hours) so you avoid
redundant repository writes and scheduler updates (refer to the FilterChip
onClick lambda, the isSelected boolean and the onIntervalSelected(hours)
callback).

105-110: Move Android-only updates UI out of commonMain.

This section is explicitly Android-only but implemented in shared source with a runtime platform check. Prefer source-set split (androidMain/jvmMain) using expect/actual or platform-specific composition entry points.

As per coding guidelines **/commonMain/**/*.kt: Shared code must be in commonMain source set and use expect/actual for platform-specific APIs; and **/{androidMain,jvmMain}/**/*.kt: Platform-specific implementations must be in androidMain and jvmMain.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@feature/profile/presentation/src/commonMain/kotlin/zed/rainxch/profile/presentation/components/sections/Installation.kt`
around lines 105 - 110, The function LazyListScope.updatesSection in common code
contains Android-only UI guarded by getPlatform() == Platform.ANDROID; move this
Android-specific implementation out of commonMain into androidMain (e.g., create
an actual implementation of an expect function or a platform-specific
composition entry point) and replace the commonMain stub with a
platform-agnostic expect declaration (or no-op) that accepts the same signature
(state: ProfileState, onAction: (ProfileAction) -> Unit). Remove the runtime
getPlatform() check from commonMain, implement the Android UI in androidMain
using the same function name (LazyListScope.updatesSection) or an actual
implementation, and keep ProfileState and ProfileAction usage consistent across
expect/actual boundaries.
core/data/src/androidMain/kotlin/zed/rainxch/core/data/services/UpdateScheduler.kt (1)

80-95: Extract shared periodic work request creation.

reschedule() duplicates the same periodic-request setup used in schedule(). A shared helper will prevent config drift (constraints/backoff) across the two paths.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@core/data/src/androidMain/kotlin/zed/rainxch/core/data/services/UpdateScheduler.kt`
around lines 80 - 95, The reschedule() and schedule() paths duplicate
PeriodicWorkRequest construction (constraints, backoff, repeatInterval) for
UpdateCheckWorker; extract that logic into a single helper function (e.g.,
buildUpdateCheckRequest or createPeriodicRequest) and have both schedule() and
reschedule() call it so constraints and backoff criteria are defined in one
place; ensure the helper returns a PeriodicWorkRequest (built with
PeriodicWorkRequestBuilder<UpdateCheckWorker> and using the same intervalHours
and TimeUnit) and replace the inline builders in schedule() and reschedule()
with a call to this helper.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In
`@composeApp/src/androidMain/kotlin/zed/rainxch/githubstore/app/GithubStoreApp.kt`:
- Around line 98-109: Replace hardcoded SELF_PACKAGE_NAME usage with the runtime
package name from the Application context (this.packageName) when checking
repo.getAppByPackage and when constructing InstalledApp, and add an early return
if packageMonitor.getInstalledPackageInfo(...) returns null so you don't persist
an InstalledApp with empty versionName/versionCode; specifically update the
logic around getInstalledPackageInfo, repo.getAppByPackage, InstalledApp
creation and persistence (and apply the same change to the other occurrence
around lines 148-150) to use runtime packageName and bail out when systemInfo is
null.

In
`@feature/profile/presentation/src/commonMain/kotlin/zed/rainxch/profile/presentation/ProfileViewModel.kt`:
- Around line 235-243: Normalize and validate the incoming update-interval value
to the supported set {3,6,12,24} before you persist it, update _state, or pass
it to any scheduler: in loadUpdateCheckInterval() wrap the collected hours from
themesRepository.getUpdateCheckInterval().collect with a normalization function
(e.g., normalizeUpdateInterval(hours)) and use the normalized value when calling
_state.update and when any scheduling functions are invoked; do the same in the
code path that writes/updates the repository (the method that saves the
interval) and in the scheduler invocation (e.g., scheduleUpdateCheck or similar)
so all writes and scheduling always use the normalized value.

---

Nitpick comments:
In
`@core/data/src/androidMain/kotlin/zed/rainxch/core/data/services/UpdateScheduler.kt`:
- Around line 80-95: The reschedule() and schedule() paths duplicate
PeriodicWorkRequest construction (constraints, backoff, repeatInterval) for
UpdateCheckWorker; extract that logic into a single helper function (e.g.,
buildUpdateCheckRequest or createPeriodicRequest) and have both schedule() and
reschedule() call it so constraints and backoff criteria are defined in one
place; ensure the helper returns a PeriodicWorkRequest (built with
PeriodicWorkRequestBuilder<UpdateCheckWorker> and using the same intervalHours
and TimeUnit) and replace the inline builders in schedule() and reschedule()
with a call to this helper.

In
`@core/data/src/commonMain/kotlin/zed/rainxch/core/data/repository/ThemesRepositoryImpl.kt`:
- Around line 118-122: The setter setUpdateCheckInterval currently writes any
Long into UPDATE_CHECK_INTERVAL_KEY via preferences.edit without validation;
update it to validate the hours parameter (e.g., require hours > 0 and
optionally enforce an upper bound) before writing to preferences—either throw an
IllegalArgumentException for invalid values or clamp to a safe range—and
document the behavior so callers of setUpdateCheckInterval know invalid inputs
are rejected or normalized.

In
`@feature/profile/presentation/src/commonMain/kotlin/zed/rainxch/profile/presentation/components/sections/Installation.kt`:
- Around line 431-434: The FilterChip onClick currently always calls
onIntervalSelected(hours) even when the option is already selected; change the
onClick handler inside the FilterChip component to first check isSelected and
return/do nothing if true, otherwise call onIntervalSelected(hours) so you avoid
redundant repository writes and scheduler updates (refer to the FilterChip
onClick lambda, the isSelected boolean and the onIntervalSelected(hours)
callback).
- Around line 105-110: The function LazyListScope.updatesSection in common code
contains Android-only UI guarded by getPlatform() == Platform.ANDROID; move this
Android-specific implementation out of commonMain into androidMain (e.g., create
an actual implementation of an expect function or a platform-specific
composition entry point) and replace the commonMain stub with a
platform-agnostic expect declaration (or no-op) that accepts the same signature
(state: ProfileState, onAction: (ProfileAction) -> Unit). Remove the runtime
getPlatform() check from commonMain, implement the Android UI in androidMain
using the same function name (LazyListScope.updatesSection) or an actual
implementation, and keep ProfileState and ProfileAction usage consistent across
expect/actual boundaries.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: c30b7cc9-8cc2-4e31-9d53-c3fcfd5db6e7

📥 Commits

Reviewing files that changed from the base of the PR and between dee34a5 and 3e43454.

📒 Files selected for processing (15)
  • composeApp/src/androidMain/kotlin/zed/rainxch/githubstore/app/GithubStoreApp.kt
  • core/data/src/androidMain/kotlin/zed/rainxch/core/data/di/PlatformModule.android.kt
  • core/data/src/androidMain/kotlin/zed/rainxch/core/data/services/AndroidUpdateScheduleManager.kt
  • core/data/src/androidMain/kotlin/zed/rainxch/core/data/services/UpdateScheduler.kt
  • core/data/src/commonMain/kotlin/zed/rainxch/core/data/repository/ThemesRepositoryImpl.kt
  • core/data/src/jvmMain/kotlin/zed/rainxch/core/data/di/PlatformModule.jvm.kt
  • core/data/src/jvmMain/kotlin/zed/rainxch/core/data/services/DesktopUpdateScheduleManager.kt
  • core/domain/src/commonMain/kotlin/zed/rainxch/core/domain/repository/ThemesRepository.kt
  • core/domain/src/commonMain/kotlin/zed/rainxch/core/domain/system/UpdateScheduleManager.kt
  • core/presentation/src/commonMain/composeResources/values/strings.xml
  • feature/profile/presentation/src/commonMain/kotlin/zed/rainxch/profile/presentation/ProfileAction.kt
  • feature/profile/presentation/src/commonMain/kotlin/zed/rainxch/profile/presentation/ProfileRoot.kt
  • feature/profile/presentation/src/commonMain/kotlin/zed/rainxch/profile/presentation/ProfileState.kt
  • feature/profile/presentation/src/commonMain/kotlin/zed/rainxch/profile/presentation/ProfileViewModel.kt
  • feature/profile/presentation/src/commonMain/kotlin/zed/rainxch/profile/presentation/components/sections/Installation.kt

Comment on lines +235 to +243
private fun loadUpdateCheckInterval() {
viewModelScope.launch {
themesRepository.getUpdateCheckInterval().collect { hours ->
_state.update {
it.copy(updateCheckIntervalHours = hours)
}
}
}
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Validate interval values before persisting/rescheduling.

hours is currently trusted end-to-end. Please normalize to supported values (3/6/12/24) before writing state/repository and before scheduling.

Suggested hardening
+    private val supportedUpdateIntervals = setOf(3L, 6L, 12L, 24L)
+    private const val defaultUpdateIntervalHours = 6L
+
+    private fun normalizeUpdateInterval(hours: Long): Long =
+        hours.takeIf { it in supportedUpdateIntervals } ?: defaultUpdateIntervalHours
+
     private fun loadUpdateCheckInterval() {
         viewModelScope.launch {
             themesRepository.getUpdateCheckInterval().collect { hours ->
+                val normalized = normalizeUpdateInterval(hours)
                 _state.update {
-                    it.copy(updateCheckIntervalHours = hours)
+                    it.copy(updateCheckIntervalHours = normalized)
                 }
             }
         }
     }
@@
             is ProfileAction.OnUpdateCheckIntervalChanged -> {
+                val normalized = normalizeUpdateInterval(action.hours)
                 viewModelScope.launch {
-                    themesRepository.setUpdateCheckInterval(action.hours)
-                    updateScheduleManager.reschedule(action.hours)
+                    themesRepository.setUpdateCheckInterval(normalized)
+                    updateScheduleManager.reschedule(normalized)
                 }
             }

Also applies to: 418-423

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@feature/profile/presentation/src/commonMain/kotlin/zed/rainxch/profile/presentation/ProfileViewModel.kt`
around lines 235 - 243, Normalize and validate the incoming update-interval
value to the supported set {3,6,12,24} before you persist it, update _state, or
pass it to any scheduler: in loadUpdateCheckInterval() wrap the collected hours
from themesRepository.getUpdateCheckInterval().collect with a normalization
function (e.g., normalizeUpdateInterval(hours)) and use the normalized value
when calling _state.update and when any scheduling functions are invoked; do the
same in the code path that writes/updates the repository (the method that saves
the interval) and in the scheduler invocation (e.g., scheduleUpdateCheck or
similar) so all writes and scheduling always use the normalized value.

- Added string resources for update check intervals (3h, 6h, 12h, 24h) and a new "Updates" section across multiple languages (ko, pl, it, ja, fr, hi, bn, es, ar, zh-rCN, ru, tr).
- Refactored self-app registration in `GithubStoreApp.kt` to improve code formatting.
- Removed unused `Logger` imports and simplified exception handling during self-registration.
Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🧹 Nitpick comments (2)
core/presentation/src/commonMain/composeResources/values-tr/strings-tr.xml (1)

524-527: Consider using a clearer Turkish hour abbreviation for interval chips.

At Line 524-527, 3s/6s/12s/24s can be ambiguous. sa (or saat) is clearer and more consistent with Line 380 usage (sa).

Suggested wording
-    <string name="interval_3h">3s</string>
-    <string name="interval_6h">6s</string>
-    <string name="interval_12h">12s</string>
-    <string name="interval_24h">24s</string>
+    <string name="interval_3h">3 sa</string>
+    <string name="interval_6h">6 sa</string>
+    <string name="interval_12h">12 sa</string>
+    <string name="interval_24h">24 sa</string>
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@core/presentation/src/commonMain/composeResources/values-tr/strings-tr.xml`
around lines 524 - 527, The interval string values interval_3h, interval_6h,
interval_12h and interval_24h use ambiguous 's' suffix; change their text to use
the clearer Turkish hour abbreviation used elsewhere (e.g., "sa" or "saat") to
match existing usage (see occurrences like the "sa" at line ~380) so that
interval_3h, interval_6h, interval_12h and interval_24h become
"3sa"/"6sa"/"12sa"/"24sa" (or "3 saat"/"6 saat"/"12 saat"/"24 saat") for
consistency and clarity.
composeApp/src/androidMain/kotlin/zed/rainxch/githubstore/app/GithubStoreApp.kt (1)

82-87: Consider adding error handling for scheduling failures.

If getUpdateCheckInterval() throws or the scheduling fails, the exception will be silently swallowed by the coroutine, leaving background update checks unscheduled without any indication.

💡 Suggested improvement
 private fun scheduleBackgroundUpdateChecks() {
     appScope.launch {
-        val intervalHours = get<ThemesRepository>().getUpdateCheckInterval().first()
-        UpdateScheduler.schedule(context = this@GithubStoreApp, intervalHours = intervalHours)
+        try {
+            val intervalHours = get<ThemesRepository>().getUpdateCheckInterval().first()
+            UpdateScheduler.schedule(context = this@GithubStoreApp, intervalHours = intervalHours)
+        } catch (e: Exception) {
+            co.touchlab.kermit.Logger.w(e) { "Failed to schedule background update checks" }
+        }
     }
 }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@composeApp/src/androidMain/kotlin/zed/rainxch/githubstore/app/GithubStoreApp.kt`
around lines 82 - 87, The scheduleBackgroundUpdateChecks function currently
launches a coroutine without error handling, so exceptions from
get<ThemesRepository>().getUpdateCheckInterval() or
UpdateScheduler.schedule(...) are swallowed; wrap the work inside
appScope.launch with a try/catch around the await of getUpdateCheckInterval()
and the call to UpdateScheduler.schedule, log or report the exception via an
existing logger (or add one) and optionally fall back to a safe default interval
or retry behavior; reference scheduleBackgroundUpdateChecks,
getUpdateCheckInterval (ThemesRepository), UpdateScheduler.schedule, and
appScope.launch when making the change.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In
`@composeApp/src/androidMain/kotlin/zed/rainxch/githubstore/app/GithubStoreApp.kt`:
- Around line 140-141: Replace the empty catch block that swallows exceptions
(catch (_: Exception) { }) in GithubStoreApp.kt with explicit handling: catch
the exception as a variable (e.g., catch (e: Exception)) and log it using
Android logging (e.g., Log.e("GithubStoreApp", "Failed while <contextual
action>", e)) or your app's logger, and consider any specific recovery
(fallback/default values or rethrow) appropriate for the operation where this
try/catch resides.

---

Nitpick comments:
In
`@composeApp/src/androidMain/kotlin/zed/rainxch/githubstore/app/GithubStoreApp.kt`:
- Around line 82-87: The scheduleBackgroundUpdateChecks function currently
launches a coroutine without error handling, so exceptions from
get<ThemesRepository>().getUpdateCheckInterval() or
UpdateScheduler.schedule(...) are swallowed; wrap the work inside
appScope.launch with a try/catch around the await of getUpdateCheckInterval()
and the call to UpdateScheduler.schedule, log or report the exception via an
existing logger (or add one) and optionally fall back to a safe default interval
or retry behavior; reference scheduleBackgroundUpdateChecks,
getUpdateCheckInterval (ThemesRepository), UpdateScheduler.schedule, and
appScope.launch when making the change.

In `@core/presentation/src/commonMain/composeResources/values-tr/strings-tr.xml`:
- Around line 524-527: The interval string values interval_3h, interval_6h,
interval_12h and interval_24h use ambiguous 's' suffix; change their text to use
the clearer Turkish hour abbreviation used elsewhere (e.g., "sa" or "saat") to
match existing usage (see occurrences like the "sa" at line ~380) so that
interval_3h, interval_6h, interval_12h and interval_24h become
"3sa"/"6sa"/"12sa"/"24sa" (or "3 saat"/"6 saat"/"12 saat"/"24 saat") for
consistency and clarity.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: ac2c2e5f-a876-400e-ab3c-99acd7330078

📥 Commits

Reviewing files that changed from the base of the PR and between 3e43454 and 2203fec.

📒 Files selected for processing (13)
  • composeApp/src/androidMain/kotlin/zed/rainxch/githubstore/app/GithubStoreApp.kt
  • core/presentation/src/commonMain/composeResources/values-ar/strings-ar.xml
  • core/presentation/src/commonMain/composeResources/values-bn/strings-bn.xml
  • core/presentation/src/commonMain/composeResources/values-es/strings-es.xml
  • core/presentation/src/commonMain/composeResources/values-fr/strings-fr.xml
  • core/presentation/src/commonMain/composeResources/values-hi/strings-hi.xml
  • core/presentation/src/commonMain/composeResources/values-it/strings-it.xml
  • core/presentation/src/commonMain/composeResources/values-ja/strings-ja.xml
  • core/presentation/src/commonMain/composeResources/values-ko/strings-ko.xml
  • core/presentation/src/commonMain/composeResources/values-pl/strings-pl.xml
  • core/presentation/src/commonMain/composeResources/values-ru/strings-ru.xml
  • core/presentation/src/commonMain/composeResources/values-tr/strings-tr.xml
  • core/presentation/src/commonMain/composeResources/values-zh-rCN/strings-zh-rCN.xml

- Replace hardcoded `SELF_PACKAGE_NAME` with the dynamic `packageName` property.
- Update `SELF_AVATAR_URL` to point to the official repository app icon.
- Integrate `kermit` logging to track self-registration success, warnings, and errors.
- Add a null check for `systemInfo` to prevent registration if package info is missing.
- Add `touchlab.kermit` dependency to `composeApp/build.gradle.kts`.
Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🧹 Nitpick comments (1)
composeApp/build.gradle.kts (1)

92-93: Optional cleanup: remove duplicate dependency.

libs.koin.compose.viewmodel is declared twice in jvmMain.dependencies. Since you're modifying this file, consider removing the duplicate.

♻️ Suggested fix
                 implementation(libs.koin.compose)
                 implementation(libs.koin.compose.viewmodel)
-                implementation(libs.koin.compose.viewmodel)
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@composeApp/build.gradle.kts` around lines 92 - 93, There is a duplicate
dependency declaration for libs.koin.compose.viewmodel in the jvmMain
dependencies block; remove the redundant
implementation(libs.koin.compose.viewmodel) entry so the dependency appears only
once (keep a single implementation(libs.koin.compose.viewmodel) line in the
jvmMain.dependencies section) and re-sync / rebuild to verify no duplicates
remain.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In
`@composeApp/src/androidMain/kotlin/zed/rainxch/githubstore/app/GithubStoreApp.kt`:
- Around line 84-87: The app startup coroutine launching scheduler
(appScope.launch) can throw from the DataStore read
get<ThemesRepository>().getUpdateCheckInterval().first() or
UpdateScheduler.schedule(...) and must be wrapped in a local try-catch to
prevent uncaught exceptions from bubbling; modify the GithubStoreApp startup
block to catch Throwable, log the failure using Logger (same pattern as
registerSelfAsInstalledApp()), and provide a safe fallback (skip scheduling) so
the app continues running if reading interval or scheduling fails.
- Around line 143-146: The success log in the try block currently uses Logger.e
which is for errors; update the success statement in the GithubStoreApp code
(where "GitHub Store App: App added" is logged) to use a non-error level such as
Logger.i or Logger.d instead, leaving the catch block's Logger.e("GitHub Store
App", e) unchanged so exceptions still log at error level.

---

Nitpick comments:
In `@composeApp/build.gradle.kts`:
- Around line 92-93: There is a duplicate dependency declaration for
libs.koin.compose.viewmodel in the jvmMain dependencies block; remove the
redundant implementation(libs.koin.compose.viewmodel) entry so the dependency
appears only once (keep a single implementation(libs.koin.compose.viewmodel)
line in the jvmMain.dependencies section) and re-sync / rebuild to verify no
duplicates remain.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: efb12599-9699-484a-b94f-b09a413927d1

📥 Commits

Reviewing files that changed from the base of the PR and between 2203fec and 82b1971.

📒 Files selected for processing (2)
  • composeApp/build.gradle.kts
  • composeApp/src/androidMain/kotlin/zed/rainxch/githubstore/app/GithubStoreApp.kt

…toreApp`

- Added a try-catch block to `scheduleBackgroundUpdateChecks` to handle and log potential failures during update scheduling.
- Replaced the hardcoded `0L` repository ID with a new `SELF_REPO_ID` constant in `registerSelfAsInstalledApp`.
- Refined logging in `registerSelfAsInstalledApp`, changing the success message to info level and improving the error log format.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant