mirror of
https://github.com/MBombeck/HealthLog.git
synced 2026-11-15 15:02:04 +00:00
Mirror the metric sub-page layout on the biomarker detail
Bring the lab biomarker detail in line with the Insights metric pages: - Lead with the static catalog description directly beneath the heading, the explainer-caption position the metric pages use. - Drop the early big-value + reference-badge block that did not match the assessment-card styling. - Split numeric and qualitative markers: numeric keeps the stat strip and chart, qualitative shows only the latest result text (no strip, no chart, no range badge). The assessment card now renders for any marker with readings and self-suppresses for qualitative-only markers. - Move the full reading history off the detail page onto a dedicated /labs/[biomarkerId]/values route, reached by a top-right list control, matching the metric pages' show-all-values affordance.
This commit is contained in:
1 parent
651b02bc1b
commit
ad43eaeff0
9 files changed
+301
-109
No files matched your search
@@ -0,0 +1,75 @@
|
||||
"use client";
|
||||
|
||||
/**
|
||||
* v1.25.1 — `/labs/[biomarkerId]/values`.
|
||||
*
|
||||
* The "show all readings" sub-page for one biomarker, mirroring the metric
|
||||
* sub-pages' `/insights/values/[type]`. The detail page keeps the
|
||||
* numbers-first spine (description → stat strip → chart → assessment) and
|
||||
* links here for the raw, editable reading feed. Owns auth + the back link to
|
||||
* the biomarker detail, and hands the marker id to `<LabValuesList>`.
|
||||
*/
|
||||
import { use, useEffect } from "react";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useQuery } from "@tanstack/react-query";
|
||||
import { Loader2 } from "lucide-react";
|
||||
|
||||
import { LabValuesList } from "@/components/labs/lab-values-list";
|
||||
import type { BiomarkerDto } from "@/components/labs/types";
|
||||
import { SubPageShell } from "@/components/insights/sub-page-shell";
|
||||
import { BackLink } from "@/components/ui/back-link";
|
||||
import { useAuth } from "@/hooks/use-auth";
|
||||
import { useMounted } from "@/hooks/use-mounted";
|
||||
import { apiGet } from "@/lib/api/api-fetch";
|
||||
import { useTranslations } from "@/lib/i18n/context";
|
||||
import { queryKeys } from "@/lib/query-keys";
|
||||
|
||||
export default function LabBiomarkerValuesPage({
|
||||
params,
|
||||
}: {
|
||||
params: Promise<{ biomarkerId: string }>;
|
||||
}) {
|
||||
const { biomarkerId } = use(params);
|
||||
const { isAuthenticated, isLoading } = useAuth();
|
||||
const mounted = useMounted();
|
||||
const router = useRouter();
|
||||
const { t } = useTranslations();
|
||||
|
||||
useEffect(() => {
|
||||
if (!isLoading && !isAuthenticated) {
|
||||
router.push("/auth/login");
|
||||
}
|
||||
}, [isLoading, isAuthenticated, router]);
|
||||
|
||||
const { data: marker } = useQuery({
|
||||
queryKey: queryKeys.biomarkerDetail(biomarkerId),
|
||||
queryFn: () => apiGet<BiomarkerDto>(`/api/biomarkers/${biomarkerId}`),
|
||||
enabled: isAuthenticated && biomarkerId.length > 0,
|
||||
});
|
||||
|
||||
if (!mounted || isLoading) {
|
||||
return (
|
||||
<div className="flex h-64 items-center justify-center">
|
||||
<Loader2 className="text-primary h-8 w-8 animate-spin motion-reduce:animate-none" />
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
const markerName = marker?.name ?? "";
|
||||
|
||||
return (
|
||||
<SubPageShell
|
||||
title={t("labs.detail.valuesTitle", { marker: markerName })}
|
||||
description={t("labs.detail.valuesDescription")}
|
||||
backLink={
|
||||
<BackLink
|
||||
href={`/labs/${biomarkerId}`}
|
||||
label={t("labs.detail.backToMarker", { marker: markerName })}
|
||||
dataSlot="lab-values-back"
|
||||
/>
|
||||
}
|
||||
>
|
||||
<LabValuesList biomarkerId={biomarkerId} />
|
||||
</SubPageShell>
|
||||
);
|
||||
}
|
||||
Reference in new issue
Block a user