The check-in counter resets on every process start, so the app may never stop asking #70
Labels
No Label
P0
P1
P2
release-blocker
No Milestone
No project
No Assignees
1 Participants
Notifications
Due Date
No due date set.
Dependencies
No dependencies set.
Reference: null/Privacy-Period-Tracker#70
Loading…
Reference in New Issue
No description provided.
Delete Branch "%!s(<nil>)"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
What is true now.
ReminderCoordinator.checkInResets(app/src/main/kotlin/dev/privacyllc/period/notifications/ReminderCoordinator.kt:116-120) isconfirmedStarts.distinctUntilChanged().onEach { if (latest != null) onPeriodConfirmed(latest) }, andonPeriodConfirmedcallspreferences.resetCheckIns()(:126-128).distinctUntilChangedonly dedups within ONE collection: a new process starts a new flow, so the first emission always passes.PeriodApplication.onCreate:42starts the coordinator in every process — including the one WorkManager spawns to runReminderWorker, which then readspreferences.checkInCount.first()(core/notifications/.../ReminderWorker.kt:91).So with any confirmed history present, the count is reset at effectively every wake-up,
MAX_CHECK_INS = 3(ReminderRules.kt:59) may never be reached, and theStopAskingbranch (ReminderRules.kt:113) may never fire.What it costs. PRODUCT_PLAN §30 (
docs/planning/PRODUCT_PLAN.md:1348) says do not nag forever. A tracker that keeps asking 'Did your period start?' every day is exactly the behaviour §30 exists to prevent, and it is the kind a user uninstalls over. No test catches it:ReminderCoordinatorTest.kt:86asserts only thatdistinctUntilChangedcollapses repeats inside one flow.What to do. Stop resetting; scope the count instead. Store the count alongside the row id of the period it was counted against, and read it as zero when the ids differ. The worker is the only reader, so no coordinator chain is needed at all — delete
checkInResets/onPeriodConfirmedand the handler's reset call.Traps. Store an id, never a date — the same reasoning that keeps dates out of
PeriodRecord.toString(). Delete My Data leaves an id matching nothing, which correctly reads as zero. Count a check-in only when the notification was actually posted (see the permission issue) or the app can stop asking having never asked.Verify:
check-ins are counted against the period they were asked aboutinUserPreferencesRepositoryTest;starting the coordinator twice on the same history leaves the check-in tally aloneinReminderCoordinatorTest;the fourth unanswered check-in is the stop-asking notice and the fifth is silencein the newReminderWorkerTest.