Fix security check notification not reappearing after dismissal#5933
Merged
Fix security check notification not reappearing after dismissal#5933
Conversation
e968a00 to
cb243ec
Compare
swansontec
requested changes
Feb 11, 2026
Contributor
swansontec
left a comment
There was a problem hiding this comment.
How about just replacing the PasswordReminderService with this:
import * as React from 'react'
import { setPasswordReminder } from '../../actions/LocalSettingsActions'
import { useAsyncEffect } from '../../hooks/useAsyncEffect'
import {
initialState,
type PasswordReminderState
} from '../../reducers/PasswordReminderReducer'
import { useDispatch, useSelector } from '../../types/reactRedux'
import { matchJson } from '../../util/matchJson'
interface Props {}
export const PasswordReminderService: React.FC<Props> = props => {
const settingsLoaded =
useSelector(state => state.ui.settings.settingsLoaded) ?? false
const passwordReminder = useSelector(state => state.ui.passwordReminder)
const lastPasswordReminder = React.useRef<PasswordReminderState>(initialState)
const dispatch = useDispatch()
useAsyncEffect(
async () => {
if (
settingsLoaded &&
!matchJson(passwordReminder, lastPasswordReminder.current)
) {
lastPasswordReminder.current = passwordReminder
await dispatch(setPasswordReminder(passwordReminder))
}
},
[settingsLoaded, passwordReminder],
'PasswordReminderService'
)
return null
}That way the useAsyncEffect runs not only on update, but also on first mount. At the same time, the code gets shorter & more modern.
| } | ||
|
|
||
| render() { | ||
| render(): React.JSX.Element | null { |
Contributor
There was a problem hiding this comment.
This should be React.ReactElement for the return type, but for some reason revcode isn't flagging it. I guess edge-conventions has too many rules to hold the agent's attention.
Contributor
Author
There was a problem hiding this comment.
Fixed — changed return type to React.ReactElement | null.
Jon-edge
commented
Feb 12, 2026
Contributor
Author
Jon-edge
left a comment
There was a problem hiding this comment.
Replaced the class component with the suggested functional component using useAsyncEffect and useRef.
swansontec
approved these changes
Feb 12, 2026
PasswordReminderService unmounts on logout and remounts after LOGIN dispatches, so componentDidUpdate never fires for the initial LOGIN transition. Add componentDidMount to persist the reducer-computed passwordReminder state (including the incremented nonPasswordLoginsCount) on mount so the count advances on disk across login cycles.
a86cb81 to
8237710
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
CHANGELOG
Does this branch warrant an entry to the CHANGELOG?
Dependencies
none
Description
Context
Asana: "Fix 'Security Check' notification trigger (reset PW)" (P0). After dismissing the Security Check modal once, it never reappears on subsequent logins — even though it should show within two non-password logins. This is the only way for users who forgot their password but can still PIN/bio login to reset it.
Regression introduced in 4.42.0 by commit
ef36815d47which consolidatedACCOUNT_INIT_COMPLETEinto theLOGINaction, changing the timing of settings initialization.Changes
PasswordReminderServiceis a class component that unmounts on logout and remounts afterLOGINdispatches. Because Redux state already contains the incrementednonPasswordLoginsCountby the time the component mounts,componentDidUpdatenever fires for the initial login transition — the "previous" and "current" props are identical from its perspective.This means the reducer-computed password reminder state (including the login counter) was never persisted to disk on login, so the count stayed stuck at a stale value across login cycles and the notification threshold was never reached.
Fix: Add
componentDidMounttoPasswordReminderServiceto persist the current reducer state to disk when the component mounts with loaded settings. This ensures thenonPasswordLoginsCountadvances on disk across login cycles without undoing the performance improvements from the originalLOGINconsolidation.Requirements
If you have made any visual changes to the GUI. Make sure you have:
Note
Medium Risk
Touches login-adjacent persistence for
passwordReminderstate; mistakes could cause reminder state to stop saving or save too often, affecting when security check prompts appear.Overview
Fixes a regression where the Security Check (password reminder) state wasn’t reliably persisted after login, so the non-password login counter could get stuck and the notification would never re-trigger.
Refactors
PasswordReminderServicefrom aconnected class component to a hooks-based service usinguseAsyncEffectand auseRefsnapshot to persistui.passwordReminderto disk once settings are loaded, including on initial mount. Adds a changelog entry for the fix.Written by Cursor Bugbot for commit 8237710. This will update automatically on new commits. Configure here.