fix: disable refetchOnWindowFocus globally to prevent modal close on tab switch - #4853
fix: disable refetchOnWindowFocus globally to prevent modal close on tab switch#4853ANSUJKMEHER wants to merge 2 commits into
Conversation
|
Updated the PR with the correct root cause fix: Reverted the onFocusOutside handler — Radix UI already handles this for modal dialogs internally, so it was redundant. Also fixes #4907 (duplicate). |
This fix addresses the issue where any modal (such as Create Database) closes immediately when the browser tab/window loses focus (blur event) or during Alt+Tab, causing users to lose all partially filled form data. Root cause: Radix UI's DismissableLayer relies on document-level focus tracking via the useFocusOutside hook. When a window blur occurs, the active input blurred event triggers onBlurCapture which sets focus-in-react-tree tracker to false. When focus is recaptured, a focusin event triggers onFocusOutside. Because DialogContent did not handle this event, it defaulted to closing the dialog. Solution: We intercept onFocusOutside inside DialogContent and invoke event.preventDefault(). This stops the event propagation to the DismissableLayer's close handler, keeping the modal open when switching windows/tabs while preserving all existing modal features (like Escape key closure, clicking outside overlay, and standard focus trapping). Fixes Dokploy#4851
…tab switch TanStack Query's refetchOnWindowFocus (default: true) causes all active queries to refetch when the browser tab regains focus. On remote servers with network latency, this re-renders the component tree and resets dialog useState(false), closing modals and losing form data. This sets refetchOnWindowFocus: false as the global default in the tRPC QueryClient config, consistent with the 14+ individual queries in the codebase that already disable it. Also reverts the redundant onFocusOutside handler in dialog.tsx — Radix UI's DialogContentModal already calls event.preventDefault() on onFocusOutside internally for modal dialogs. Fixes Dokploy#4851 Fixes Dokploy#4907
d479d31 to
10050b8
Compare
|
Hi @Siumauricio , just following up on this PR. I updated it based on my investigation and narrowed the fix down to disabling All checks are passing now. If you have a chance, I'd really appreciate a review. Thanks! |
Summary
Disables TanStack Query's
refetchOnWindowFocusglobally to prevent dialog/modal forms from closing and losing data when the browser tab or window regains focus.Fixes #4851
Fixes #4907
Root Cause
TanStack Query's
refetchOnWindowFocusdefaults totrue. When the user switches away from Dokploy and returns:focusevent fires on the windowproject.one,environment.one,project.all)useState(false)→ modal closes, form data lostThis is timing/latency dependent — it reproduces reliably on remote servers but rarely on localhost (where queries complete instantly and
structuralSharingreturns the same reference).Changes
apps/dokploy/utils/api.tsqueryClientConfig.defaultOptions.queries.refetchOnWindowFocus: falseto the global tRPC configrefetchOnWindowFocus: falseper-query (e.g., inuse-whitelabeling.ts,dashboard-layout.tsx,side.tsx,handle-destinations.tsx, etc.)apps/dokploy/components/ui/dialog.tsxonFocusOutsidehandler that was redundant — Radix UI'sDialogContentModalalready callsevent.preventDefault()ononFocusOutsideinternally for modal dialogs (source)Testing
refetchOnWindowFocus: falseconfig is correctly accepted bycreateTRPCNext'squeryClientConfigoption@radix-ui/react-dialog,@radix-ui/react-dismissable-layer,@radix-ui/primitive) to confirm theonFocusOutsidehandler was redundant