From 6b35cad079c14f8ebce0bb0755abf03b55c5ff8b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc-Andr=C3=A9=20Bombeck?= Date: Sun, 10 May 2026 14:24:35 +0200 Subject: [PATCH] refactor(v1.4.19): apply simplify-review safe suggestions MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Mechanical clean-up sweep across five hot spots flagged by the simplify audit: - Lift the 11-key auth.* audit-action label map out of the two admin components that rebuilt it on every render. The shared useAuthActionLabels() hook in _shared.tsx is now the single home for new entries (login-overview + recent-audit-preview consume it). - Drop the dead chipClass branches in IntegrationStatusPill: only the connected state actually paints a Dracula-green chip; error and disconnected fall back to the badge variant. - Add thin DateInput / DateTimeInput wrappers under components/ui that bake in the lang={locale} hint so 14 callsites across 9 files no longer have to remember the prop. A future date input cannot silently regress. - Remove the leading icon-only flex wrappers left behind when the duplicate card titles were dropped on /admin/feedback, /admin/danger-zone, and the thresholds editor. - Strip the five "v1.4.19 X removed because…" narration comments from insights/page.tsx and the dashboard. git blame already answers what changed and the comments aged into history. Co-Authored-By: Claude Opus 4.7 (1M context) --- src/app/insights/page.tsx | 46 +------------------ src/app/onboarding/page.tsx | 5 +- src/app/page.tsx | 11 ----- src/components/admin/_shared.tsx | 29 ++++++++++++ src/components/admin/danger-zone-section.tsx | 10 ++-- .../admin/feedback-inbox-section.tsx | 4 +- .../admin/login-overview-section.tsx | 16 +------ src/components/admin/recent-audit-preview.tsx | 16 +------ .../doctor-report/doctor-report-dialog.tsx | 11 ++--- .../measurements/measurement-form.tsx | 7 ++- .../measurements/measurement-list.tsx | 7 ++- .../medications/intake-history-list.tsx | 20 +++----- src/components/mood/mood-form.tsx | 7 ++- src/components/mood/mood-list.tsx | 7 ++- src/components/settings/account-section.tsx | 5 +- src/components/settings/export-section.tsx | 12 ++--- .../settings/integration-status-pill.tsx | 12 ++--- .../settings/thresholds-editor-section.tsx | 10 ++-- src/components/ui/date-input.tsx | 28 +++++++++++ 19 files changed, 108 insertions(+), 155 deletions(-) create mode 100644 src/components/ui/date-input.tsx diff --git a/src/app/insights/page.tsx b/src/app/insights/page.tsx index e7bdaf870..ff6ecfa4f 100644 --- a/src/app/insights/page.tsx +++ b/src/app/insights/page.tsx @@ -221,13 +221,6 @@ interface MedicationComplianceDailyResponse { dailyCompliance: Record; } -/** - * v1.4.19 A3 — `getRangeColorClass` / `getRangeHint` / - * `RangeDisplayConfig` removed alongside the `` tile-strip - * deletion. Those helpers were only used by the duplicate-of-dashboard - * tile grid; every other call site lives on the dashboard surface. - */ - /** * v1.4.16 phase B1b — pick the freshest ISO timestamp from a list so the * page hero's "Generated …" caption surfaces a single representative @@ -645,10 +638,6 @@ export default function InsightsPage() { const sys = analytics?.summaries?.BLOOD_PRESSURE_SYS; const dia = analytics?.summaries?.BLOOD_PRESSURE_DIA; const p = analytics?.summaries?.PULSE; - // v1.4.19 A3 — `bf` / `showBodyFatCard` / `moodSummary` / - // `showMoodCard` were bookkeeping for the now-removed duplicate - // tile strip (Marc said those tiles duplicate the dashboard). - // Remaining mood references read `data?.moodSummary` inline below. const bmiDivisor = user?.heightCm ? (user.heightCm / 100) ** 2 : null; // bmiAvg30 and bmiSlope30 still used for overallStatus + bmiSectionStatus const bmiAvg30 = bmiDivisor && w?.avg30 != null ? w.avg30 / bmiDivisor : null; @@ -853,12 +842,6 @@ export default function InsightsPage() { return (
- {/* v1.4.19 A3 — comparison toggle is now mounted INSIDE the hero - meta band (alongside personal-baseline indicator + Generated - timestamp + Regenerate button). The previous standalone band - below the hero made the page read as three stacked cards - with separate header / control rows; folding the toggle into - the hero clusters every page-level control in one place. */} ` (severity-ordered recommendations grid + per-rec rationale expand + confidence meter + thumbs feedback + - medical-citation footnotes) into the live route. Before this - fix the page rendered only the text-only `` - per section, hiding all of B5c/d/e/B1b's polish from users. - The per-section status cards stay below as supplemental detail. - - v1.4.19 A3 — `onRegenerate` is no longer wired here. The page - hero already owns the single page-level refresh affordance; - the card-level icon button + empty-state "Analyse starten" - button were duplicates that surfaced the same handler three - ways (page hero button, card-header icon button, - empty-state CTA). The per-recommendation Regenerate (inside - ``) is unrelated — it stays under the - v1.4.16 spec. The placeholder `aiOverviewTitle` - ("Persönlicher Berater") subtitle is also gone — the - CardTitle ("KI-Gesundheitsanalyse") is enough framing on its - own, and the orphan title above an empty body when the user - has no provider configured was the actual confusion source - Marc reported. */} + medical-citation footnotes) into the live route. The + per-section status cards stay below as supplemental detail. */} - {/* v1.4.19 A3 — duplicate per-metric `` strip removed. - Up to v1.4.18 the page led with a 5-column grid of weight / - BP-sys / BP-dia / pulse / body-fat / mood tiles — exact - duplicates of the dashboard tile-strip. They added zero - information beyond what's already on the dashboard. The - recommendations grid + per-section detail cards below are - the actual value on `/insights`; the tiles only consumed - scroll height. */} -

diff --git a/src/app/onboarding/page.tsx b/src/app/onboarding/page.tsx index 6fad41252..19547818c 100644 --- a/src/app/onboarding/page.tsx +++ b/src/app/onboarding/page.tsx @@ -16,6 +16,7 @@ import { import { Button } from "@/components/ui/button"; import { Input } from "@/components/ui/input"; +import { DateInput } from "@/components/ui/date-input"; import { Label } from "@/components/ui/label"; import { Logo } from "@/components/ui/logo"; import { MeasurementForm } from "@/components/measurements/measurement-form"; @@ -301,10 +302,8 @@ export default function OnboardingPage() {
- setDateOfBirth(e.target.value)} max={new Date().toISOString().slice(0, 10)} diff --git a/src/app/page.tsx b/src/app/page.tsx index a639549ac..c936722df 100644 --- a/src/app/page.tsx +++ b/src/app/page.tsx @@ -491,17 +491,6 @@ export default function DashboardPage() {
- {/* v1.4.19 A3 — comparison toggle removed from dashboard. - The tile strip is too tight for an extra control band, and - Marc rarely wants Vormonat / Vorjahr context at a glance — - when he does, it's on `/insights` where the chart sits next - to the toggle. The underlying `compareBaseline` value still - flows from `/api/dashboard/widgets` into every chart below - so nothing visual changes when the user has the comparison - on; only the on-surface affordance moves. Settings → - Dashboard remains the power-user backdoor for either - surface. */} - {/* v1.4: Getting-started checklist for brand-new users. * Self-gates visibility on (onboardingCompletedAt == null * || measurementCount < 5) and disappears once dismissed diff --git a/src/components/admin/_shared.tsx b/src/components/admin/_shared.tsx index f34a2c3b8..7f3541f68 100644 --- a/src/components/admin/_shared.tsx +++ b/src/components/admin/_shared.tsx @@ -1,5 +1,6 @@ "use client"; +import { useMemo } from "react"; import { useQuery, useMutation, useQueryClient } from "@tanstack/react-query"; import { toast } from "sonner"; import { Switch } from "@/components/ui/switch"; @@ -257,6 +258,34 @@ export async function getApiErrorMessage(response: Response): Promise { return fallback; } +/** + * Shared `auth.*` audit-action label map. Two surfaces consume it + * today (`/admin/login-overview` and the dashboard recent-activity + * preview), and any future audit feed will need the same translation + * lookup. New auth actions are added here once instead of being + * copy-pasted into every consumer. + */ +export function useAuthActionLabels(): Record { + const { t, locale } = useTranslations(); + return useMemo( + () => ({ + "auth.register": t("admin.authRegister"), + "auth.login": t("admin.authLogin"), + "auth.login.passkey": t("admin.authLoginPasskey"), + "auth.login.password": t("admin.authLoginPassword"), + "auth.login.failed": t("admin.authLoginFailed"), + "auth.logout": t("admin.authLogout"), + "auth.passkey.register": t("admin.authPasskeyRegister"), + "auth.passkey.delete": t("admin.authPasskeyDelete"), + "auth.token.autoissue.native": t("admin.authTokenAutoissueNative"), + "auth.token.refresh": t("admin.authTokenRefresh"), + "auth.token.revoke": t("admin.authTokenRevoke"), + }), + // eslint-disable-next-line react-hooks/exhaustive-deps + [locale], + ); +} + export function useSystemStatus() { return useQuery({ queryKey: ["admin", "status"], diff --git a/src/components/admin/danger-zone-section.tsx b/src/components/admin/danger-zone-section.tsx index 0f6240a24..460ce0311 100644 --- a/src/components/admin/danger-zone-section.tsx +++ b/src/components/admin/danger-zone-section.tsx @@ -70,12 +70,10 @@ export function DangerZoneSection() { already names the section, so the card-level title was a duplicate of the page title. The destructive icon stays so the card still flags itself as dangerous at a glance. */} -
-
+