I am building a React + Vite application and have a scenario where a process is in progress. When I click the browser refresh, the default browser confirmation dialog appears. I have written a custom hook to prevent browser back navigation and show a warning modal. However, on refresh, the default browser dialog still appears.
Here’s the hook I wrote:
import { useEffect } from "react"
import { useBlocker } from "react-router-dom"
const useBrowserActions = (props: TProps) => {
const { getBlock, onBlockedState, showWaring } = props
const { state, proceed, reset } = useBlocker(({ currentLocation, nextLocation }) =>
getBlock(currentLocation?.pathname, nextLocation?.pathname)
)
useEffect(() => {
if (state === "blocked") onBlockedState()
}, [state])
useEffect(() => {
const handleBeforeUnload = (e: BeforeUnloadEvent) => {
if (!showWaring) return
e.preventDefault()
e.returnValue = ""
return ""
}
window.addEventListener("beforeunload", handleBeforeUnload)
return () => window.removeEventListener("beforeunload", handleBeforeUnload)
}, [showWaring])
return { proceed, reset, state }
}
export default useBrowserActions
type TProps = {
getBlock: (currentLocation: string, nextLocation: string) => boolean
onBlockedState: () => void | Promise
showWaring?: boolean
}
This works fine in Chrome and Edge. In Firefox, the browser back handling works, and the default dialog shows on refresh. However, if I click refresh again, the page reloads immediately without showing the dialog. This behavior does not happen in Chrome or Edge.
If anyone has encountered this issue in Firefox and has a solution, please help!