Add avatars, profiles, and auth flows

This commit is contained in:
Micha
2026-01-12 23:40:11 +01:00
parent bbbf8eb6c1
commit 3bb2946656
30 changed files with 691 additions and 48 deletions

View File

@@ -10,10 +10,19 @@ import Register from './pages/Register'
import Acp from './pages/Acp'
import BoardIndex from './pages/BoardIndex'
import Ucp from './pages/Ucp'
import Profile from './pages/Profile'
import { useTranslation } from 'react-i18next'
import { fetchSettings, fetchVersion, getForum, getThread } from './api/client'
function PortalHeader({ userMenu, isAuthenticated, forumName, logoUrl, showHeaderName }) {
function PortalHeader({
userMenu,
isAuthenticated,
forumName,
logoUrl,
showHeaderName,
canAccessAcp,
canAccessMcp,
}) {
const { t } = useTranslation()
const location = useLocation()
const [crumbs, setCrumbs] = useState([])
@@ -107,7 +116,7 @@ function PortalHeader({ userMenu, isAuthenticated, forumName, logoUrl, showHeade
}, [location.pathname, t])
return (
<Container className="pt-2 pb-2 bb-portal-shell">
<Container fluid className="pt-2 pb-2 bb-portal-shell">
<div className="bb-portal-banner">
<div className="bb-portal-brand">
{logoUrl && (
@@ -135,12 +144,18 @@ function PortalHeader({ userMenu, isAuthenticated, forumName, logoUrl, showHeade
<span>
<i className="bi bi-question-circle-fill" aria-hidden="true" /> {t('portal.link_faq')}
</span>
<Link to="/acp" className="bb-portal-link">
<i className="bi bi-gear-fill" aria-hidden="true" /> {t('portal.link_acp')}
</Link>
<span>
<i className="bi bi-hammer" aria-hidden="true" /> {t('portal.link_mcp')}
</span>
{isAuthenticated && canAccessAcp && (
<>
<Link to="/acp" className="bb-portal-link">
<i className="bi bi-gear-fill" aria-hidden="true" /> {t('portal.link_acp')}
</Link>
</>
)}
{isAuthenticated && canAccessMcp && (
<span>
<i className="bi bi-hammer" aria-hidden="true" /> {t('portal.link_mcp')}
</span>
)}
</div>
</div>
<div
@@ -197,7 +212,7 @@ function PortalHeader({ userMenu, isAuthenticated, forumName, logoUrl, showHeade
function AppShell() {
const { t } = useTranslation()
const { token, email, logout, isAdmin } = useAuth()
const { token, email, userId, logout, isAdmin, isModerator } = useAuth()
const [versionInfo, setVersionInfo] = useState(null)
const [theme, setTheme] = useState('auto')
const [resolvedTheme, setResolvedTheme] = useState('light')
@@ -403,7 +418,7 @@ function AppShell() {
<NavDropdown.Item as={Link} to="/ucp">
<i className="bi bi-sliders" aria-hidden="true" /> {t('portal.user_control_panel')}
</NavDropdown.Item>
<NavDropdown.Item as={Link} to="/ucp">
<NavDropdown.Item as={Link} to={`/profile/${userId ?? ''}`}>
<i className="bi bi-person" aria-hidden="true" /> {t('portal.user_profile')}
</NavDropdown.Item>
<NavDropdown.Divider />
@@ -413,6 +428,8 @@ function AppShell() {
</NavDropdown>
) : null
}
canAccessAcp={isAdmin}
canAccessMcp={isModerator}
/>
<Routes>
<Route path="/" element={<Home />} />
@@ -421,6 +438,7 @@ function AppShell() {
<Route path="/thread/:id" element={<ThreadView />} />
<Route path="/login" element={<Login />} />
<Route path="/register" element={<Register />} />
<Route path="/profile/:id" element={<Profile />} />
<Route path="/acp/*" element={<Acp isAdmin={isAdmin} />} />
<Route
path="/ucp"