import { useState, useEffect } from 'react' import { Outlet, useLocation } from 'react-router-dom' import Sidebar from './components/Sidebar' import OperationsBar from './components/OperationsBar' import { ToastContainer, useToast } from './components/Toast' import { systemApi } from './utils/api' const COLLAPSED_KEY = 'localai_sidebar_collapsed' export default function App() { const [sidebarOpen, setSidebarOpen] = useState(false) const [sidebarCollapsed, setSidebarCollapsed] = useState(() => { try { return localStorage.getItem(COLLAPSED_KEY) === 'true' } catch (_) { return false } }) const { toasts, addToast, removeToast } = useToast() const [version, setVersion] = useState('') const location = useLocation() const isChatRoute = location.pathname.match(/\/chat(\/|$)/) || location.pathname.match(/\/agents\/[^/]+\/chat/) useEffect(() => { systemApi.version() .then(data => setVersion(typeof data === 'string' ? data : (data?.version || ''))) .catch(() => {}) }, []) useEffect(() => { const handler = (e) => setSidebarCollapsed(e.detail.collapsed) window.addEventListener('sidebar-collapse', handler) return () => window.removeEventListener('sidebar-collapse', handler) }, []) const layoutClasses = [ 'app-layout', isChatRoute ? 'app-layout-chat' : '', sidebarCollapsed ? 'sidebar-is-collapsed' : '', ].filter(Boolean).join(' ') return (
setSidebarOpen(false)} />
{/* Mobile header */}
LocalAI
{!isChatRoute && ( )}
) }