BillTracker/client/App.jsx

89 lines
2.6 KiB
React
Raw Normal View History

2026-05-03 19:51:57 -05:00
import { Routes, Route, Navigate, useLocation } from 'react-router-dom';
import { useAuth } from '@/hooks/useAuth';
import Layout from '@/components/layout/Layout';
import { ReleaseNotesDialog } from '@/components/ReleaseNotesDialog';
import LoginPage from '@/pages/LoginPage';
import AdminPage from '@/pages/AdminPage';
import TrackerPage from '@/pages/TrackerPage';
import BillsPage from '@/pages/BillsPage';
import CategoriesPage from '@/pages/CategoriesPage';
import SettingsPage from '@/pages/SettingsPage';
import StatusPage from '@/pages/StatusPage';
import ReleaseNotesPage from '@/pages/ReleaseNotesPage';
import DataPage from '@/pages/DataPage';
import ProfilePage from '@/pages/ProfilePage';
function RequireAuth({ children, role }) {
const { user, singleUserMode } = useAuth();
const location = useLocation();
// Loading state
if (user === undefined) {
return (
<div className="flex items-center justify-center min-h-screen bg-background text-muted-foreground text-sm">
Loading...
</div>
);
}
// Single-user mode bypass
if (singleUserMode && role === 'user') return children;
// Not authenticated
if (!user) {
return <Navigate to="/login" state={{ from: location }} replace />;
}
2026-05-03 20:40:48 -05:00
const roleAllowed = !role || user.role === role || (role === 'user' && user.role === 'admin');
2026-05-03 19:51:57 -05:00
// Role mismatch
2026-05-03 20:40:48 -05:00
if (!roleAllowed) {
2026-05-03 19:51:57 -05:00
return <Navigate to={user.role === 'admin' ? '/admin' : '/'} replace />;
}
return children;
}
export default function App() {
const { user } = useAuth();
return (
<>
{/* Release notes (only for user role) */}
{user?.role === 'user' && <ReleaseNotesDialog />}
<Routes>
<Route path="/login" element={<LoginPage />} />
<Route
path="/admin"
element={
<RequireAuth role="admin">
<AdminPage />
</RequireAuth>
}
/>
<Route
element={
<RequireAuth role="user">
<Layout />
</RequireAuth>
}
>
<Route index element={<TrackerPage />} />
<Route path="bills" element={<BillsPage />} />
<Route path="categories" element={<CategoriesPage />} />
<Route path="settings" element={<SettingsPage />} />
<Route path="data" element={<DataPage />} />
<Route path="profile" element={<ProfilePage />} />
<Route path="status" element={<StatusPage />} />
<Route path="release-notes" element={<ReleaseNotesPage />} />
<Route path="*" element={<Navigate to="/" replace />} />
</Route>
</Routes>
</>
);
}