fix(sidebar): omit changelog badge for anon visitors + clarify CLAUDE.md auth gate (t-paliad-035)
The marketing landing (`/`) renders the same Sidebar as protected pages, so `initChangelogBadge()` was firing `GET /api/changelog/unseen-count` on every anon visit and getting 401. Cosmetic noise + wasted round-trip. Add an `authenticated` prop to Sidebar (defaults to true, no behavior change on protected pages) and pass `false` from `renderIndex()`. The badge `<a>` is omitted server-side; the existing `if (!badge) return` guard in sidebar.ts naturally skips the fetch when the element is absent — no client change needed. Also append a clarifying note under the env-var table in .claude/CLAUDE.md: "work without DB" doesn't mean "ungated for anon". The knowledge-platform routes (Kostenrechner, Glossar, etc.) are still behind the auth gate; only `/`, `/login`, `/logout`, and `/assets/*` are public. Misread by the smoke tester briefer; spelled out now to prevent recurrence.
This commit is contained in:
@@ -48,6 +48,8 @@ Paliad — the patent paladin. All-in-one patent practice platform for HLC (form
|
||||
| `SMTP_HOST` / `SMTP_PORT` / `SMTP_USERNAME` / `SMTP_PASSWORD` / `SMTP_FROM` / `SMTP_FROM_NAME` / `SMTP_USE_TLS` | for email | SMTP credentials for Paliad's transactional mail (reminders, invitations). Port 465 uses implicit TLS. `MailService` silently no-ops when any required var is missing — the server still boots for knowledge-platform-only deployments. |
|
||||
| `ANTHROPIC_API_KEY` | not used today | Reserved for Phase H (AI Frist-Extraktion) which is deferred per m's 2026-04-16 decision. Do not set. |
|
||||
|
||||
> *Note on `DATABASE_URL`:* "Work without DB" ≠ "ungated". All knowledge-platform routes (Kostenrechner, Glossar, Links, Gebührentabellen, Checklisten, Gerichte, Downloads) are still behind the auth gate (302 to `/login` for anon visitors); only `/`, `/login`, `/logout`, and `/assets/*` are public. The `gateOnboarded` middleware additionally blocks unonboarded users from app pages but does NOT gate the knowledge-platform pages.
|
||||
|
||||
## Infrastructure
|
||||
|
||||
- **Gitea:** `mAi/paliad` on mgit.msbls.de (renamed from mAi/patholo — auto-redirects)
|
||||
|
||||
@@ -25,6 +25,12 @@ const ICON_USERS = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" s
|
||||
|
||||
interface SidebarProps {
|
||||
currentPath: string;
|
||||
// authenticated defaults to true; pass false on anon-facing pages (the
|
||||
// marketing landing) so we don't render auth-only affordances that would
|
||||
// fire 401s. Currently gates only the changelog badge link — the badge
|
||||
// client (sidebar.ts initChangelogBadge) early-returns when the link is
|
||||
// absent, so there is no client change needed.
|
||||
authenticated?: boolean;
|
||||
}
|
||||
|
||||
function navItem(href: string, icon: string, i18nKey: string, label: string, currentPath: string): string {
|
||||
@@ -60,7 +66,7 @@ function group(i18nKey: string, label: string, children: string): string {
|
||||
);
|
||||
}
|
||||
|
||||
export function Sidebar({ currentPath }: SidebarProps): string {
|
||||
export function Sidebar({ currentPath, authenticated = true }: SidebarProps): string {
|
||||
return (
|
||||
<Fragment>
|
||||
<aside className="sidebar">
|
||||
@@ -129,11 +135,13 @@ export function Sidebar({ currentPath }: SidebarProps): string {
|
||||
<div className="sidebar-spacer" />
|
||||
|
||||
<div className="sidebar-bottom">
|
||||
<a href="/changelog" className={`sidebar-item sidebar-changelog${currentPath === "/changelog" ? " active" : ""}`} id="sidebar-changelog-link">
|
||||
<span className="sidebar-icon" dangerouslySetInnerHTML={{ __html: ICON_SPARKLE }} />
|
||||
<span className="sidebar-label" data-i18n="nav.neuigkeiten">Neuigkeiten</span>
|
||||
<span className="sidebar-badge" id="sidebar-changelog-badge" style="display:none" aria-hidden="true" />
|
||||
</a>
|
||||
{authenticated ? (
|
||||
<a href="/changelog" className={`sidebar-item sidebar-changelog${currentPath === "/changelog" ? " active" : ""}`} id="sidebar-changelog-link">
|
||||
<span className="sidebar-icon" dangerouslySetInnerHTML={{ __html: ICON_SPARKLE }} />
|
||||
<span className="sidebar-label" data-i18n="nav.neuigkeiten">Neuigkeiten</span>
|
||||
<span className="sidebar-badge" id="sidebar-changelog-badge" style="display:none" aria-hidden="true" />
|
||||
</a>
|
||||
) : ""}
|
||||
<button type="button" className="sidebar-item sidebar-invite-btn" id="sidebar-invite-btn">
|
||||
<span className="sidebar-icon" dangerouslySetInnerHTML={{ __html: ICON_MAIL }} />
|
||||
<span className="sidebar-label" data-i18n="invite.button">Kolleg:in einladen</span>
|
||||
|
||||
@@ -23,7 +23,7 @@ export function renderIndex(): string {
|
||||
<link rel="stylesheet" href="/assets/global.css" />
|
||||
</head>
|
||||
<body className="has-sidebar">
|
||||
<Sidebar currentPath="/" />
|
||||
<Sidebar currentPath="/" authenticated={false} />
|
||||
|
||||
<main>
|
||||
<section className="hero">
|
||||
|
||||
Reference in New Issue
Block a user