diff --git a/src/components/insights/__tests__/health-score-card.test.tsx b/src/components/insights/__tests__/health-score-card.test.tsx index a5c467cde..f30bfe79b 100644 --- a/src/components/insights/__tests__/health-score-card.test.tsx +++ b/src/components/insights/__tests__/health-score-card.test.tsx @@ -20,7 +20,11 @@ import { type Translate, } from "../health-score-pillar-detail"; -let mockAuthUser: { unitPreference: string; glucoseUnit: string } = { +let mockAuthUser: { + unitPreference: string; + glucoseUnit: string; + timezone?: string; +} = { unitPreference: "metric", glucoseUnit: "mg/dL", }; @@ -624,14 +628,21 @@ describe(" composite states", () => { const html = render( , ); const rest = atRest(html); - expect(rest).toContain("Rest Mode active since 2026-07-20"); + // The onset is an instant; it reads as the day it falls on in the + // profile timezone, in the user's date format, never as raw ISO. + expect(rest).toMatch(/Rest Mode active since \d{2}\/\d{2}\/2026\./); + expect(rest).not.toContain("T23:30:00"); expect(rest).toContain('data-slot="health-score-tension"'); expect(rest).toContain('data-slot="health-score-return-to-band"'); // The contributor key and the metric type are localised, never raw. @@ -640,6 +651,28 @@ describe(" composite states", () => { expect(rest).not.toContain(">rhr<"); }); + it("reads the Rest Mode onset as the day in the profile timezone", () => { + mockAuthUser = { + unitPreference: "metric", + glucoseUnit: "mg/dL", + timezone: "Europe/Berlin", + }; + const html = render( + , + ); + const rest = atRest(html); + expect(rest).toMatch(/Rest Mode active since (07\/20\/2026|20\/07\/2026)/); + expect(rest).not.toContain("2026-07-19T"); + }); + it("shows the weekly gain as a chip beside the label", () => { const html = render(); expect(html).toContain('data-slot="health-score-card-label"'); diff --git a/src/components/insights/health-score-card.tsx b/src/components/insights/health-score-card.tsx index a9780bf2d..45b3d5302 100644 --- a/src/components/insights/health-score-card.tsx +++ b/src/components/insights/health-score-card.tsx @@ -24,6 +24,8 @@ import { type PillarDetailContext, } from "@/components/insights/health-score-pillar-detail"; import { useAuth } from "@/hooks/use-auth"; +import { formatDate } from "@/lib/date-format"; +import { DEFAULT_TIMEZONE, userDayKey } from "@/lib/tz/format"; import { useUnitDisplay } from "@/hooks/use-unit-display"; import { resolveGlucoseUnit } from "@/lib/glucose"; import type { @@ -31,7 +33,7 @@ import type { ScoreBand, ScorePillarResult, } from "@/lib/analytics/score/types"; -import { useTranslations } from "@/lib/i18n/context"; +import { useDateFormatPreference, useTranslations } from "@/lib/i18n/context"; import { SCORE_PILLAR_LABEL_KEYS } from "@/lib/score-config/labels"; import { cn } from "@/lib/utils"; @@ -265,7 +267,8 @@ export function HealthScoreCard({ onRetry, className, }: HealthScoreCardProps) { - const { t } = useTranslations(); + const { t, locale } = useTranslations(); + const dateFormat = useDateFormatPreference(); const { user } = useAuth(); const [open, setOpen] = useState(false); const regionId = useId(); @@ -528,7 +531,16 @@ export function HealthScoreCard({ className="text-muted-foreground text-xs" > {t("insights.healthScore.restMode", { - since: report.restMode.since ?? t("insights.healthScore.none"), + since: report.restMode.since + ? formatDate( + userDayKey( + new Date(report.restMode.since), + user?.timezone || DEFAULT_TIMEZONE, + ), + dateFormat, + locale, + ) + : t("insights.healthScore.none"), })}

) : null}