mirror of
https://github.com/diegosouzapw/OmniRoute.git
synced 2026-08-01 21:02:12 +03:00
fix(offline): avoid SSR/CSR hydration mismatch on navigator.onLine
Replace useState+lazy-initializer with useSyncExternalStore so the server snapshot (() => false) and client snapshot (() => navigator.onLine) are declared separately. React hydrates with the server value and switches to the real online status client-side without a mismatch.
This commit is contained in:
@@ -1,25 +1,24 @@
|
||||
"use client";
|
||||
|
||||
import { useEffect, useState } from "react";
|
||||
import { useSyncExternalStore } from "react";
|
||||
import Link from "next/link";
|
||||
|
||||
function subscribeToOnline(callback: () => void) {
|
||||
window.addEventListener("online", callback);
|
||||
window.addEventListener("offline", callback);
|
||||
return () => {
|
||||
window.removeEventListener("online", callback);
|
||||
window.removeEventListener("offline", callback);
|
||||
};
|
||||
}
|
||||
|
||||
export default function OfflinePage() {
|
||||
const [isOnline, setIsOnline] = useState<boolean>(() =>
|
||||
typeof navigator !== "undefined" ? navigator.onLine : true
|
||||
const isOnline = useSyncExternalStore(
|
||||
subscribeToOnline,
|
||||
() => navigator.onLine,
|
||||
() => false
|
||||
);
|
||||
|
||||
useEffect(() => {
|
||||
const onOnline = () => setIsOnline(true);
|
||||
const onOffline = () => setIsOnline(false);
|
||||
|
||||
window.addEventListener("online", onOnline);
|
||||
window.addEventListener("offline", onOffline);
|
||||
return () => {
|
||||
window.removeEventListener("online", onOnline);
|
||||
window.removeEventListener("offline", onOffline);
|
||||
};
|
||||
}, []);
|
||||
|
||||
return (
|
||||
<main className="min-h-screen bg-bg text-text-main flex items-center justify-center p-6">
|
||||
<section className="w-full max-w-xl rounded-2xl border border-border bg-surface p-8 shadow-soft text-center">
|
||||
|
||||
Reference in New Issue
Block a user