…igation
OnboardingStore._onMoveToPreviousPage had no bounds check, so rapid back-
button clicks (or any double-dispatch of the action) could pop the last
entry off _pageStack, leaving it empty. page() then returned undefined,
causing OnboardingRoot.render() to throw "Cannot find component for page:
undefined" (Sentry MAILSPRING-CLIENT-26, 23 users).
Two-layer fix:
1. Guard in _onMoveToPreviousPage: bail out if the stack has only one page,
so the stack can never be emptied through back-navigation.
2. Defensive fallback in OnboardingRoot.render: if page is still somehow
undefined, close/quit the window gracefully instead of throwing.
Fixes MAILSPRING-CLIENT-26
https://claude.ai/code/session_01PGz7rfpJU4fs2QMeT7sdYw
Summary
Fixes Sentry issue MAILSPRING-CLIENT-26 — 23 users affected, 59 occurrences.
Error:
Cannot find component for page: undefinedLocation:
OnboardingRoot.render()inonboarding-root.tsxRoot Cause
OnboardingStore._onMoveToPreviousPagepops from_pageStackwith no bounds check. If the action fires when only one page is on the stack (e.g. rapid back-button double-clicks, or any duplicate dispatch ofmoveToPreviousPage), the stack becomes empty.page()then returnsundefined, andOnboardingRoot.render()throws an unhandled error instead of degrading gracefully.The stale-closure risk in
PageTopBar:closeActioncapturespageDepthfrom props at render time. A rapid double-click could fire both handlers withpageDepth = 2before the re-render reflecting the first pop, triggeringmoveToPreviousPage()twice in succession and draining the stack to zero.Fix (two layers)
onboarding-store.ts— Guard in_onMoveToPreviousPage: bail out early if the stack has only one page, making it impossible to empty the stack via back-navigation.onboarding-root.tsx— Defensive fallback inrender(): ifpageis somehow still undefined (any future unknown cause), close/quit the window gracefully instead of throwing an unhandled exception that reaches Sentry.Test plan
https://claude.ai/code/session_01PGz7rfpJU4fs2QMeT7sdYw
Generated by Claude Code