import React from 'react'; import { QueryClient, QueryClientProvider } from '@tanstack/react-query'; import { AppRouter } from '@/routes'; import { setUnauthorizedHandler } from '@/api/client'; import { useAuthStore } from '@/store/authStore'; import { useThemeStore } from '@/store/themeStore'; import { ErrorBoundary } from '@/components/common/ErrorBoundary'; import { useToast } from '@/components/ui/Toast'; import { useOnlineStatus } from '@/hooks/useOnlineStatus'; import { CommandPalette } from '@/components/search/CommandPalette'; import { useCommandPalette } from '@/hooks/useCommandPalette'; function QueryClientWrapper({ children }: { children: React.ReactNode }) { const toast = useToast(); const [queryClient] = React.useState(() => new QueryClient({ defaultOptions: { queries: { retry: 1, staleTime: 5 * 60 * 1000, refetchOnWindowFocus: false, }, mutations: { retry: 0, onError: (error: any) => { // Don't show toast for 401 (handled by auth) if (error?.status === 401) return; const msg = error?.detail || error?.message || 'Ein Fehler ist aufgetreten'; toast.error(msg); }, }, }, })); return ( {children} ); } function OfflineBanner() { const isOnline = useOnlineStatus(); if (isOnline) return null; return (
Sie sind offline. Änderungen werden gespeichert wenn die Verbindung wiederhergestellt ist.
); } export default function App() { const { logout } = useAuthStore(); const loadThemeFromStorage = useThemeStore((s) => s.loadFromStorage); const toast = useToast(); React.useEffect(() => { setUnauthorizedHandler(() => { toast.warning('Ihre Sitzung ist abgelaufen. Sie werden zur Anmeldung weitergeleitet.'); logout(); setTimeout(() => { window.location.href = '/login'; }, 1500); }); }, [logout, toast]); // Load theme from localStorage on app start React.useEffect(() => { loadThemeFromStorage(); }, [loadThemeFromStorage]); return ( Zum Hauptinhalt springen ); }