MCPcopy Create free account
hub / github.com/ShipSecAI/studio / ProtectedRoute

Function ProtectedRoute

frontend/src/components/auth/ProtectedRoute.tsx:20–218  ·  view source on GitHub ↗
({
  children,
  fallback,
  requireAuth = true,
  requireOrg = false,
  roles = [],
  redirectTo,
})

Source from the content-addressed store, hash-verified

18}
19
20export const ProtectedRoute: React.FC<ProtectedRouteProps> = ({
21 children,
22 fallback,
23 requireAuth = true,
24 requireOrg = false,
25 roles = [],
26 redirectTo,
27}) => {
28 // All hooks must be called unconditionally at the top
29 const { isAuthenticated, isLoading, user } = useAuth();
30 const authProvider = useAuthProvider();
31 const { openSignIn, isOpen, close } = useAuthModal();
32 const adminUsername = useAuthStore((state) => state.adminUsername);
33 const adminPassword = useAuthStore((state) => state.adminPassword);
34
35 // Track whether we've attempted to open the sign-in dialog
36 const [signInAttempted, setSignInAttempted] = useState(false);
37
38 // Function to trigger sign-in (can be called manually)
39 const triggerSignIn = useCallback(() => {
40 if (authProvider.name === 'clerk') {
41 setSignInAttempted(true);
42 authProvider.signIn();
43 }
44 }, [authProvider]);
45
46 // Automatically trigger sign-in for Clerk when not authenticated (only once on mount)
47 useEffect(() => {
48 if (
49 !isLoading &&
50 !isAuthenticated &&
51 requireAuth &&
52 authProvider.name === 'clerk' &&
53 !signInAttempted
54 ) {
55 triggerSignIn();
56 }
57 }, [isLoading, isAuthenticated, requireAuth, authProvider, signInAttempted, triggerSignIn]);
58
59 // Reset signInAttempted when user becomes authenticated (for future sign-outs)
60 useEffect(() => {
61 if (isAuthenticated) {
62 setSignInAttempted(false);
63 }
64 }, [isAuthenticated]);
65
66 // Compute derived values after hooks
67 const isLocalAuth = authProvider.name === 'local';
68 const hasLocalCredentials = !!(adminUsername && adminPassword);
69
70 // Show loading state
71 if (isLoading) {
72 return (
73 <div className="flex items-center justify-center min-h-96">
74 <div className="flex items-center space-x-2 text-muted-foreground">
75 <Shield className="w-6 h-6 animate-pulse" />
76 <span>Checking authentication...</span>
77 </div>

Callers

nothing calls this directly

Calls 3

useAuthFunction · 0.90
useAuthProviderFunction · 0.90
useAuthModalFunction · 0.90

Tested by

no test coverage detected