import { useState } from 'react'; import { Outlet, useNavigate } from 'react-router-dom'; import { Menu, Sun, Moon, Bell, LogOut, User, Globe, KeyRound, Save } from 'lucide-react'; import { NavigationView } from '../components/NavigationView.jsx'; import { Flyout, FlyoutItem, FlyoutSeparator } from '../components/Flyout.jsx'; import { DetailPopup } from '../components/DetailPopup.jsx'; import { Field } from '../components/Field.jsx'; import { Button } from '../components/Button.jsx'; import { PasswordInput } from '../components/PasswordInput.jsx'; import { useAuth } from '../context/auth-context.jsx'; import { useUi } from '../context/ui-context.jsx'; import { useAsync } from '../hooks/useAsync.js'; import { listNotifications, markAllNotificationsRead, markNotificationRead } from '../services/notifications.js'; import { changePassword } from '../services/auth.js'; const EMPTY_PASSWORD_FORM = { currentPassword: '', newPassword: '', confirmPassword: '' }; export default function AppShell() { const [navMode, setNavMode] = useState('expanded'); const { user, logout } = useAuth(); const { t, theme, setTheme, lang, setLang, pushToast } = useUi(); const navigate = useNavigate(); const { data: notifData, reload: reloadNotifications } = useAsync(listNotifications, []); const unread = notifData?.unread || 0; const [changingPassword, setChangingPassword] = useState(false); const [passwordForm, setPasswordForm] = useState(EMPTY_PASSWORD_FORM); const [passwordError, setPasswordError] = useState(''); function toggleNav() { setNavMode((m) => (m === 'expanded' ? 'compact' : 'expanded')); } async function handleNotificationClick(notification) { if (!notification.is_read) await markNotificationRead(notification.id); await reloadNotifications(); if (notification.entity_type === 'project') navigate(`/proyectos/${notification.entity_id}`); else if (notification.entity_type === 'activity') navigate(`/proyectos`); } function openChangePassword() { setPasswordForm(EMPTY_PASSWORD_FORM); setPasswordError(''); setChangingPassword(true); } async function submitChangePassword() { setPasswordError(''); if (passwordForm.newPassword !== passwordForm.confirmPassword) { setPasswordError(t('register_password_mismatch')); return; } if (passwordForm.newPassword.length < 8) { setPasswordError(t('register_password_short')); return; } try { await changePassword(passwordForm.currentPassword, passwordForm.newPassword); setChangingPassword(false); pushToast({ tone: 'success', message: t('change_password_success') }); } catch (err) { setPasswordError(err.message || t('common_error')); } } return (