finalizing app adn fixes
This commit is contained in:
32
frontend/src/components/auth/AdminRoute.tsx
Normal file
32
frontend/src/components/auth/AdminRoute.tsx
Normal file
@@ -0,0 +1,32 @@
|
||||
import { ReactNode } from "react";
|
||||
import { Navigate, useLocation } from "react-router-dom";
|
||||
import { useAuthStore } from "../../store/authStore";
|
||||
|
||||
interface AdminRouteProps {
|
||||
children: ReactNode;
|
||||
}
|
||||
|
||||
/**
|
||||
* AdminRoute component - guards routes requiring admin or staff privileges
|
||||
* Redirects to dashboard if user is not admin/staff
|
||||
*/
|
||||
export default function AdminRoute({ children }: AdminRouteProps) {
|
||||
const { user, isAuthenticated } = useAuthStore();
|
||||
const location = useLocation();
|
||||
|
||||
// If not authenticated, ProtectedRoute will handle redirect
|
||||
if (!isAuthenticated) {
|
||||
return null;
|
||||
}
|
||||
|
||||
// Check if user is admin or staff
|
||||
const isAdmin = user?.role === 'admin' || user?.is_staff === true;
|
||||
|
||||
if (!isAdmin) {
|
||||
// Redirect non-admin users to dashboard
|
||||
console.log('AdminRoute: User is not admin/staff, redirecting to dashboard');
|
||||
return <Navigate to="/" state={{ from: location }} replace />;
|
||||
}
|
||||
|
||||
return <>{children}</>;
|
||||
}
|
||||
@@ -13,6 +13,7 @@ import { WorkflowInsights, WorkflowInsight } from './WorkflowInsights';
|
||||
|
||||
interface PageHeaderProps {
|
||||
title: string;
|
||||
description?: string; // Optional page description shown below title
|
||||
lastUpdated?: Date;
|
||||
showRefresh?: boolean;
|
||||
onRefresh?: () => void;
|
||||
@@ -28,6 +29,7 @@ interface PageHeaderProps {
|
||||
|
||||
export default function PageHeader({
|
||||
title,
|
||||
description,
|
||||
lastUpdated,
|
||||
showRefresh = false,
|
||||
onRefresh,
|
||||
@@ -116,6 +118,9 @@ export default function PageHeader({
|
||||
)}
|
||||
<h2 className="text-2xl font-bold text-gray-800 dark:text-white/90">{title}</h2>
|
||||
</div>
|
||||
{description && (
|
||||
<p className="text-sm text-gray-500 dark:text-gray-400 mt-1 max-w-xl">{description}</p>
|
||||
)}
|
||||
{!hideSiteSector && (
|
||||
<div className="flex items-center gap-3 mt-1">
|
||||
{lastUpdated && (
|
||||
|
||||
Reference in New Issue
Block a user