Editor's "Back to Workspace" Link navigates silently with no unsaved-changes warning — beforeunload (#161) only covers tab close, not in-app Link navigation #184
Labels
No labels
blocked:commit-ready-failed
blocked:gate-fetch
blocked:gate-lint
blocked:gate-plan
blocked:gate-research
blocked:needs-attention
blocked:needs-decision
blocked:needs-human
blocked:no-changes
blocked:verify-failed
bug
deferred
feature-request
in-progress
needs-decompose
needs-triage
quickfix
security/medium
triage-approved
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set.
Reference
Mark/Kimi_Agent_Brother_10_Digitizing_App#184
Loading…
Add table
Add a link
Reference in a new issue
No description provided.
Delete branch "%!s()"
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?
Finding
src/components/editor/EditorHeader.tsx:188-204renders the "Back to Workspace" button as a React Router<Link to="/workspace">. The Link has noonClickconfirmation. If the user has unsaved edits (state.isDirty is true per the #161 wiring), clicking the Link navigates away without prompting.The
beforeunloadhandler registered inEditor.tsx(per #161) only fires forwindow.beforeunload— i.e., the user closing the tab, refreshing, or closing the window. React Router-driven navigation within the SPA does NOT firebeforeunload. The comment at the handler explicitly notes: "React Router-driven navigations within the SPA don't firebeforeunload, so this only covers refresh / tab-close / window-close, which matches the finding's scope (sessionStorage round-trips still carry the edit on in-app navigation)."The current behavior is: the user edits, clicks "Back to Workspace", the editor unmounts, the sessionStorage snapshot remains. The user can re-open the editor and find their work, but the explicit "you have unsaved changes" prompt never appears.
Where
src/components/editor/EditorHeader.tsx:188-204— the<Link to="/workspace">elementSuggested fix shape
Add an
onClickhandler to the Link that confirms navigation when isDirty:This requires plumbing
isDirtyfromEditor.tsxintoEditorHeaderas a new prop (alongsidecanSave,onSave, etc).For the keyboard shortcut equivalent, the same confirmation would need to fire on the navbar's nav clicks and the back button. A shared
useUnsavedChangesGuard(isDirty)hook would centralize this.Severity
Medium. The user can lose context (not work) by clicking away from the editor. The sessionStorage round-trip is a safety net but the user doesn't know about it.
Discovered by
Gap analysis (2026-10-02) of editor unsaved-changes handling.
Related
Closed via commit
56033cfon main.Fix:
isDirtyprop; the Back-to-Workspace<Link>now callswindow.confirm(...)when isDirty is true, ande.preventDefault()if the user cancels.isDirty(already in scope from #161) into EditorHeader.19/19 EditorHeader tests pass; 9/9 Editor tests pass; tsc -b clean; eslint clean on the touched files.
Scope kept tight to the suggested fix shape; the broader
useUnsavedChangesGuardhook is intentionally deferred — there is no second consumer yet (keyboard shortcut, navbar nav, back button), so the abstraction would be premature.