Grace period doesn't survive leaving via Back.AppLockViewModel/AppLockGate are scoped to MainActivity's ViewModelStore via hiltViewModel(). On API 29/30, Back on the root destination finishes the activity and clears the store, so re-entry 2 s later re-arms a fresh LOCKED gate and demands full re-auth — while leaving via Home and returning within 30 s stays unlocked. Behaves differently on API 31+ (root Back moves the task to back). Contradicts the documented 30 s grace rule the JVM tests pin.
PassphraseSession is never re-locked on timeout. Its KDoc promises the passphrase is "cleared on lock, timeout," but no code path calls session.lock() on gate re-lock/grace expiry — only onAuthError/RETRY call gate.lock(), never session.lock(). The UI gate is Activity-scoped while the secret is a process-scoped @Singleton plus an already-open Room handle, so a "locked" app still holds the raw passphrase in memory for the process lifetime. Doc/impl mismatch that a future "evict on timeout" feature will trip over (it also needs a DB close/reopen mechanism, since provideDatabase runs once per process).
Suggested fix
Hoist the grace/lock state so it survives activity recreation (application-scoped, or persist backgroundedAt), and either implement session eviction on re-lock (with the DB-handle lifecycle it requires) or correct the KDoc to state the accepted limitation explicitly. Relates to the two-tier gate/secret design.
Origin: code review of PR #45 (screen-lock app gate). Below-the-cut lifecycle-consistency items.
## Problem
- **Grace period doesn't survive leaving via Back.** `AppLockViewModel`/`AppLockGate` are scoped to `MainActivity`'s ViewModelStore via `hiltViewModel()`. On API 29/30, Back on the root destination finishes the activity and clears the store, so re-entry 2 s later re-arms a fresh LOCKED gate and demands full re-auth — while leaving via Home and returning within 30 s stays unlocked. Behaves differently on API 31+ (root Back moves the task to back). Contradicts the documented 30 s grace rule the JVM tests pin.
- **`PassphraseSession` is never re-locked on timeout.** Its KDoc promises the passphrase is "cleared on lock, timeout," but no code path calls `session.lock()` on gate re-lock/grace expiry — only `onAuthError`/RETRY call `gate.lock()`, never `session.lock()`. The UI gate is Activity-scoped while the secret is a process-scoped `@Singleton` plus an already-open Room handle, so a "locked" app still holds the raw passphrase in memory for the process lifetime. Doc/impl mismatch that a future "evict on timeout" feature will trip over (it also needs a DB close/reopen mechanism, since `provideDatabase` runs once per process).
## Suggested fix
Hoist the grace/lock state so it survives activity recreation (application-scoped, or persist `backgroundedAt`), and either implement session eviction on re-lock (with the DB-handle lifecycle it requires) or correct the KDoc to state the accepted limitation explicitly. Relates to the two-tier gate/secret design.
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Origin: code review of PR #45 (screen-lock app gate). Below-the-cut lifecycle-consistency items.
Problem
AppLockViewModel/AppLockGateare scoped toMainActivity's ViewModelStore viahiltViewModel(). On API 29/30, Back on the root destination finishes the activity and clears the store, so re-entry 2 s later re-arms a fresh LOCKED gate and demands full re-auth — while leaving via Home and returning within 30 s stays unlocked. Behaves differently on API 31+ (root Back moves the task to back). Contradicts the documented 30 s grace rule the JVM tests pin.PassphraseSessionis never re-locked on timeout. Its KDoc promises the passphrase is "cleared on lock, timeout," but no code path callssession.lock()on gate re-lock/grace expiry — onlyonAuthError/RETRY callgate.lock(), neversession.lock(). The UI gate is Activity-scoped while the secret is a process-scoped@Singletonplus an already-open Room handle, so a "locked" app still holds the raw passphrase in memory for the process lifetime. Doc/impl mismatch that a future "evict on timeout" feature will trip over (it also needs a DB close/reopen mechanism, sinceprovideDatabaseruns once per process).Suggested fix
Hoist the grace/lock state so it survives activity recreation (application-scoped, or persist
backgroundedAt), and either implement session eviction on re-lock (with the DB-handle lifecycle it requires) or correct the KDoc to state the accepted limitation explicitly. Relates to the two-tier gate/secret design.