Spaces:
Running
Running
File size: 7,932 Bytes
09801ca | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 | import { BrowserRouter, Routes, Route, Navigate } from 'react-router-dom';
import React, { useEffect, useState, useCallback, Suspense } from 'react';
import { AnimatePresence } from 'framer-motion';
import { AuthProvider } from './contexts/AuthContext';
import { ToastProvider } from './contexts/ToastContext';
import { useUserStore } from './store/userStore';
import SplashScreen from './components/SplashScreen';
import { Loader2 } from 'lucide-react';
import Landing from './pages/Landing';
import Login from './pages/Login';
import AuthCallback from './pages/AuthCallback';
import AppLayout from './components/layout/AppLayout';
import ProtectedRoute from './components/ProtectedRoute';
// Lazy load non-critical routes for performance optimization
const DataHub = React.lazy(() => import('./pages/DataHub'));
const AnalystChat = React.lazy(() => import('./pages/AnalystChat'));
const Reports = React.lazy(() => import('./pages/Reports'));
const Settings = React.lazy(() => import('./pages/Settings'));
const NotificationSettings = React.lazy(() => import('./pages/NotificationSettings'));
const Signup = React.lazy(() => import('./pages/Signup'));
const AcceptInvite = React.lazy(() => import('./pages/AcceptInvite'));
const ForgotPassword = React.lazy(() => import('./pages/ForgotPassword'));
const UpdatePassword = React.lazy(() => import('./pages/UpdatePassword'));
const EmailConfirm = React.lazy(() => import('./pages/EmailConfirm'));
const AutonomousDashboard = React.lazy(() => import('./pages/AutonomousDashboard'));
const MLPredictions = React.lazy(() => import('./pages/MLPredictions'));
const Clustering = React.lazy(() => import('./pages/Clustering'));
const ScenarioSimulator = React.lazy(() => import('./pages/ScenarioSimulator'));
const DataLineage = React.lazy(() => import('./pages/DataLineage'));
const Collaborate = React.lazy(() => import('./pages/Collaborate'));
const Developer = React.lazy(() => import('./pages/Developer'));
const ComputerVision = React.lazy(() => import('./pages/ComputerVision'));
const Autopilot = React.lazy(() => import('./pages/Autopilot'));
const PrivacyPolicy = React.lazy(() => import('./pages/PrivacyPolicy'));
const TermsOfService = React.lazy(() => import('./pages/TermsOfService'));
const HelpCenter = React.lazy(() => import('./pages/HelpCenter'));
const DataStories = React.lazy(() => import('./pages/DataStories'));
const PipelineBuilder = React.lazy(() => import('./pages/PipelineBuilder'));
const EmbedWidget = React.lazy(() => import('./pages/EmbedWidget'));
const AdminLogin = React.lazy(() => import('./pages/AdminLogin'));
const AdminDashboard = React.lazy(() => import('./pages/AdminDashboard'));
function App() {
const [showSplash, setShowSplash] = useState(false); // Splash screen disabled
const { isDark, accentTheme } = useUserStore();
// Apply theme on mount & changes
useEffect(() => {
// 1. Dark/Light Mode
if (isDark) {
document.documentElement.classList.remove('light-theme');
document.documentElement.classList.add('dark');
document.body.classList.remove('light-theme');
} else {
document.documentElement.classList.add('light-theme');
document.documentElement.classList.remove('dark');
document.body.classList.add('light-theme');
}
// 2. Accent Theme
// Remove all existing accent themes
document.documentElement.classList.forEach(className => {
if (className.startsWith('theme-')) {
document.documentElement.classList.remove(className);
}
});
// Add new accent theme
if (accentTheme && accentTheme !== 'default') {
document.documentElement.classList.add(`theme-${accentTheme}`);
}
}, [isDark, accentTheme]);
const handleSplashComplete = useCallback(() => {
setShowSplash(false);
}, []);
return (
<>
<AnimatePresence>
{showSplash && (
<SplashScreen onComplete={handleSplashComplete} />
)}
</AnimatePresence>
<BrowserRouter>
<AuthProvider>
<ToastProvider>
<Suspense fallback={<div className="flex h-screen w-full items-center justify-center bg-[var(--bg-primary)]"><div className="w-10 h-10 border-4 border-indigo-500 border-t-transparent rounded-full animate-spin"></div></div>}>
<Routes>
{/* Public routes */}
<Route path="/" element={<Landing />} />
<Route path="/login" element={<Login />} />
<Route path="/signup" element={<Signup />} />
<Route path="/accept-invite" element={<AcceptInvite />} />
<Route path="/forgot-password" element={<ForgotPassword />} />
<Route path="/auth/update-password" element={<UpdatePassword />} />
<Route path="/auth/callback" element={<AuthCallback />} />
<Route path="/auth/confirm" element={<EmailConfirm />} />
{/* Legal & Help Pages */}
<Route path="/privacy" element={<PrivacyPolicy />} />
<Route path="/terms" element={<TermsOfService />} />
<Route path="/help" element={<HelpCenter />} />
{/* Redirect /overview to /data-hub */}
<Route path="/overview" element={<Navigate to="/data-hub" replace />} />
{/* Standalone Embedded Widget */}
<Route path="/embed/:widgetId" element={<EmbedWidget />} />
{/* Admin Console — separate from normal user auth */}
<Route path="/admin" element={<AdminLogin />} />
<Route path="/admin/dashboard" element={<AdminDashboard />} />
{/* Chat - Full screen without main navigation */}
<Route path="/chat" element={
<ProtectedRoute>
<AnalystChat />
</ProtectedRoute>
} />
{/* Embed Widgets - Standalone, unauthenticated (token-based) route */}
<Route path="/embed/:widgetId" element={<EmbedWidget />} />
{/* Protected routes wrapped in AppLayout */}
<Route element={<ProtectedRoute><AppLayout /></ProtectedRoute>}>
<Route path="/dashboard" element={<AutonomousDashboard />} />
<Route path="/data-hub" element={<DataHub />} />
<Route path="/datahub" element={<DataHub />} />
<Route path="/ml-predictions" element={<MLPredictions />} />
<Route path="/pipelines" element={<PipelineBuilder />} />
<Route path="/clustering" element={<Clustering />} />
{/* V3 New Pages */}
<Route path="/simulator" element={<ScenarioSimulator />} />
<Route path="/autopilot" element={<Autopilot />} />
<Route path="/lineage" element={<DataLineage />} />
<Route path="/collaborate" element={<Collaborate />} />
<Route path="/developer" element={<Developer />} />
<Route path="/computer-vision" element={<ComputerVision />} />
<Route path="/reports" element={<Reports />} />
<Route path="/data-stories" element={<DataStories />} />
<Route path="/settings" element={<Settings />} />
<Route path="/settings/notifications" element={<NotificationSettings />} />
{/* Legacy redirects */}
<Route path="/automl" element={<Navigate to="/ml-predictions" replace />} />
</Route>
{/* Redirect any unknown route to home */}
<Route path="*" element={<Navigate to="/" replace />} />
</Routes>
</Suspense>
</ToastProvider>
</AuthProvider>
</BrowserRouter>
</>
);
}
export default App;
|