mirror of
https://github.com/MBombeck/HealthLog.git
synced 2026-11-13 06:32:03 +00:00
refactor(insights): migrate route slugs to english with redirects
Rename every routed Insights sub-page slug from German to English (`/insights/blutdruck` -> `/insights/blood-pressure`, `gewicht` -> `weight`, `medikamente` -> `medications`, and the full v1.7.0 metric tail). UI copy stays localised through `t()` keys; only the internal slugs change. The slug registry in `src/lib/insights/sub-page-metric.ts` is the single source of truth, so the tab strip, target summary, and daily-briefing routing targets follow it. `next.config.ts` `redirects()` emits a permanent redirect from every legacy German slug to its English target, including a `:path*` variant so nested routes survive. Bookmarks and cached PWA navigation keep resolving.
This commit is contained in:
1 parent
b416cabbf1
commit
c4ccd7e297
46 files changed
+244
-180
No files matched your search
@@ -4,7 +4,7 @@
|
||||
* Returns a chronological merge of every GLP-1-relevant event the user
|
||||
* has logged: dose changes, injections (with site if recorded),
|
||||
* inventory events, and side-effect-tagged mood entries from the
|
||||
* trailing 90 days. Used by /insights/medikamente's TherapyTimeline
|
||||
* trailing 90 days. Used by /insights/medications' TherapyTimeline
|
||||
* component. Web-only users without a GLP-1 medication get
|
||||
* `hasGlp1: false` so the component hides cleanly.
|
||||
*/
|
||||
|
||||
@@ -5,7 +5,7 @@ import { Flame } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.4.32 — `/insights/aktive-energie`.
|
||||
* v1.4.32 — `/insights/active-energy`.
|
||||
*
|
||||
* Active-energy-burned sub-page. The MeasurementType is cumulative
|
||||
* (kcal per day, per R-A Option A); the v1.4.30 server-side daily-
|
||||
@@ -5,7 +5,7 @@ import { Volume2 } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/laermereignisse`.
|
||||
* v1.7.0 — `/insights/audio-events`.
|
||||
*
|
||||
* AUDIO_EXPOSURE_EVENT sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { Droplet } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/blutzucker`.
|
||||
* v1.7.0 — `/insights/blood-glucose`.
|
||||
*
|
||||
* BLOOD_GLUCOSE sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -18,7 +18,7 @@ import { SubPageShell } from "@/components/insights/sub-page-shell";
|
||||
import { getBpTargets } from "@/lib/analytics/bp-targets";
|
||||
|
||||
/**
|
||||
* v1.4.25 W4 — `/insights/blutdruck`.
|
||||
* v1.4.25 W4 — `/insights/blood-pressure`.
|
||||
*
|
||||
* Routed Blood-Pressure sub-page. The mother page hosts the overview
|
||||
* (hero + briefing + advisor); this page concentrates on BP-only depth:
|
||||
@@ -114,7 +114,7 @@ export default function InsightsBlutdruckPage() {
|
||||
userTimezone={user?.timezone}
|
||||
/>
|
||||
|
||||
<MetricTargetSummary slug="blutdruck" />
|
||||
<MetricTargetSummary slug="blood-pressure" />
|
||||
|
||||
<InsightStatusCard
|
||||
title={t("insights.assessmentTitle")}
|
||||
+1
-1
@@ -5,7 +5,7 @@ import { Thermometer } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.4.32 — `/insights/koerpertemperatur`.
|
||||
* v1.4.32 — `/insights/body-temperature`.
|
||||
*
|
||||
* Body-temperature sub-page. Canonical storage is Celsius. Distinct
|
||||
* from skin temperature (Withings ScanWatch dermal reading) — surface
|
||||
@@ -5,7 +5,7 @@ import { Droplet } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/koerperwasser`.
|
||||
* v1.7.0 — `/insights/body-water`.
|
||||
*
|
||||
* TOTAL_BODY_WATER sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { Bone } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/knochenmasse`.
|
||||
* v1.7.0 — `/insights/bone-mass`.
|
||||
*
|
||||
* BONE_MASS sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { Sun } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/tageslicht`.
|
||||
* v1.7.0 — `/insights/daylight`.
|
||||
*
|
||||
* TIME_IN_DAYLIGHT sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
+1
-1
@@ -5,7 +5,7 @@ import { Footprints } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/doppelstandphase`.
|
||||
* v1.7.0 — `/insights/double-support-time`.
|
||||
*
|
||||
* WALKING_DOUBLE_SUPPORT sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
+1
-1
@@ -5,7 +5,7 @@ import { Volume2 } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/laermbelastung`.
|
||||
* v1.7.0 — `/insights/environmental-audio`.
|
||||
*
|
||||
* AUDIO_EXPOSURE_ENV sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { Scale } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/fettfreie-masse`.
|
||||
* v1.7.0 — `/insights/fat-free-mass`.
|
||||
*
|
||||
* FAT_FREE_MASS sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { Droplets } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/fettmasse`.
|
||||
* v1.7.0 — `/insights/fat-mass`.
|
||||
*
|
||||
* FAT_MASS sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { TrendingUp } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/stockwerke`.
|
||||
* v1.7.0 — `/insights/flights-climbed`.
|
||||
*
|
||||
* FLIGHTS_CLIMBED sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
+1
-1
@@ -5,7 +5,7 @@ import { Headphones } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/kopfhoererpegel`.
|
||||
* v1.7.0 — `/insights/headphone-audio`.
|
||||
*
|
||||
* AUDIO_EXPOSURE_HEADPHONE sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { Scale } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/magermasse`.
|
||||
* v1.7.0 — `/insights/lean-body-mass`.
|
||||
*
|
||||
* LEAN_BODY_MASS sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -21,7 +21,7 @@ import { TherapyTimeline } from "@/components/insights/therapy-timeline";
|
||||
import { MedicationCardHeader } from "@/components/medications/MedicationCardHeader";
|
||||
|
||||
/**
|
||||
* v1.4.25 W4 — `/insights/medikamente`.
|
||||
* v1.4.25 W4 — `/insights/medications`.
|
||||
*
|
||||
* Routed Medication-Compliance sub-page. Mirrors the per-medication
|
||||
* grid from the v1.4.24 mother page (compliance bars + heatmap +
|
||||
@@ -166,7 +166,7 @@ export default function InsightsMedikamentePage() {
|
||||
{medications.map((med) => {
|
||||
const medicationSummary = medicationSummaryById.get(med.id);
|
||||
// UI-H3 — route every medication-list row (medications page
|
||||
// + insights/medikamente) through `<MedicationCardHeader>`
|
||||
// + insights/medications) through `<MedicationCardHeader>`
|
||||
// so the surface stays one shape: `{name} {dose}` on line 1
|
||||
// + outline category badge on line 2. The streak chip rides
|
||||
// the `stateBadges` slot so a strong streak still surfaces.
|
||||
@@ -243,7 +243,7 @@ export default function InsightsMedikamentePage() {
|
||||
})}
|
||||
</div>
|
||||
|
||||
<MetricTargetSummary slug="medikamente" />
|
||||
<MetricTargetSummary slug="medications" />
|
||||
|
||||
<InsightStatusCard
|
||||
title={t("insights.assessmentTitle")}
|
||||
@@ -19,7 +19,7 @@ import { MetricTargetSummary } from "@/components/insights/metric-target-summary
|
||||
import { SubPageShell } from "@/components/insights/sub-page-shell";
|
||||
|
||||
/**
|
||||
* v1.4.25 W4 — `/insights/stimmung`.
|
||||
* v1.4.25 W4 — `/insights/mood`.
|
||||
*
|
||||
* Routed Mood sub-page. Unlike the mother page (which hid the mood
|
||||
* section entirely when no mood data existed), a dedicated sub-page
|
||||
@@ -105,7 +105,7 @@ export default function InsightsStimmungPage() {
|
||||
userTimezone={user?.timezone}
|
||||
/>
|
||||
|
||||
<MetricTargetSummary slug="stimmung" />
|
||||
<MetricTargetSummary slug="mood" />
|
||||
|
||||
<InsightStatusCard
|
||||
title={t("insights.assessmentTitle")}
|
||||
@@ -5,7 +5,7 @@ import { Dumbbell } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/muskelmasse`.
|
||||
* v1.7.0 — `/insights/muscle-mass`.
|
||||
*
|
||||
* MUSCLE_MASS sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { Wind } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.4.32 — `/insights/sauerstoff`.
|
||||
* v1.4.32 — `/insights/oxygen`.
|
||||
*
|
||||
* Oxygen-saturation (SpO₂) sub-page. Canonical storage is percent
|
||||
* (0..100); the chart axis runs 85..100 because clinical normal is
|
||||
+1
-1
@@ -5,7 +5,7 @@ import { Activity } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/pulswellengeschwindigkeit`.
|
||||
* v1.7.0 — `/insights/pulse-wave-velocity`.
|
||||
*
|
||||
* PULSE_WAVE_VELOCITY sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -22,7 +22,7 @@ import {
|
||||
} from "@/lib/analytics/pulse-targets";
|
||||
|
||||
/**
|
||||
* v1.4.25 W4 — `/insights/puls`.
|
||||
* v1.4.25 W4 — `/insights/pulse`.
|
||||
*
|
||||
* Routed Pulse sub-page. Renders the pulse chart with the personalized
|
||||
* Karvonen-derived target band plus the per-section AI assessment.
|
||||
@@ -126,7 +126,7 @@ export default function InsightsPulsPage() {
|
||||
userTimezone={user?.timezone}
|
||||
/>
|
||||
|
||||
<MetricTargetSummary slug="puls" />
|
||||
<MetricTargetSummary slug="pulse" />
|
||||
|
||||
<InsightStatusCard
|
||||
title={t("insights.assessmentTitle")}
|
||||
@@ -5,7 +5,7 @@ import { Wind } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/atemfrequenz`.
|
||||
* v1.7.0 — `/insights/respiratory-rate`.
|
||||
*
|
||||
* RESPIRATORY_RATE sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,9 +5,9 @@ import { Heart } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.4.32 — `/insights/ruhepuls`.
|
||||
* v1.4.32 — `/insights/resting-pulse`.
|
||||
*
|
||||
* Resting-heart-rate sub-page. Distinct from `/insights/puls` — Apple
|
||||
* Resting-heart-rate sub-page. Distinct from `/insights/pulse` — Apple
|
||||
* Health splits the steady-state daily `restingHeartRate` value from
|
||||
* the spot `PULSE` samples logged manually or by Withings. The split
|
||||
* here mirrors that distinction so the user has a "daily floor"
|
||||
+1
-1
@@ -5,7 +5,7 @@ import { Thermometer } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/hauttemperatur`.
|
||||
* v1.7.0 — `/insights/skin-temperature`.
|
||||
*
|
||||
* SKIN_TEMPERATURE sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -13,7 +13,7 @@ import { SleepOverview } from "@/components/insights/sleep-overview";
|
||||
import { SubPageShell } from "@/components/insights/sub-page-shell";
|
||||
|
||||
/**
|
||||
* v1.4.25 W4c — `/insights/schlaf`.
|
||||
* v1.4.25 W4c — `/insights/sleep`.
|
||||
*
|
||||
* The Sleep sub-page surfaces the per-stage breakdown + duration trend
|
||||
* the v1.4.23 schema gained but never rendered. All charts live inside
|
||||
@@ -65,7 +65,7 @@ export default function InsightsSchlafPage() {
|
||||
>
|
||||
<SleepOverview />
|
||||
|
||||
<MetricTargetSummary slug="schlaf" />
|
||||
<MetricTargetSummary slug="sleep" />
|
||||
|
||||
{/*
|
||||
v1.4.28 (BK-UI-StatusSchlaf) — the six sibling sub-pages all
|
||||
@@ -5,7 +5,7 @@ import { Footprints } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/schrittlaenge`.
|
||||
* v1.7.0 — `/insights/step-length`.
|
||||
*
|
||||
* WALKING_STEP_LENGTH sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { HeartPulse } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/gefaessalter`.
|
||||
* v1.7.0 — `/insights/vascular-age`.
|
||||
*
|
||||
* VASCULAR_AGE sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { Droplets } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/viszeralfett`.
|
||||
* v1.7.0 — `/insights/visceral-fat`.
|
||||
*
|
||||
* VISCERAL_FAT sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
+1
-1
@@ -5,7 +5,7 @@ import { Footprints } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/gangasymmetrie`.
|
||||
* v1.7.0 — `/insights/walking-asymmetry`.
|
||||
*
|
||||
* WALKING_ASYMMETRY sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { Footprints } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/gehstrecke`.
|
||||
* v1.7.0 — `/insights/walking-distance`.
|
||||
*
|
||||
* WALKING_RUNNING_DISTANCE sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -5,7 +5,7 @@ import { HeartPulse } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/gehpuls`.
|
||||
* v1.7.0 — `/insights/walking-heart-rate`.
|
||||
*
|
||||
* WALKING_HEART_RATE_AVERAGE sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
+1
-1
@@ -5,7 +5,7 @@ import { Gauge } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/gehgeschwindigkeit`.
|
||||
* v1.7.0 — `/insights/walking-speed`.
|
||||
*
|
||||
* WALKING_SPEED sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
+1
-1
@@ -5,7 +5,7 @@ import { Gauge } from "lucide-react";
|
||||
import { HealthKitMetricPage } from "@/components/insights/healthkit-metric-page";
|
||||
|
||||
/**
|
||||
* v1.7.0 — `/insights/gangstabilitaet`.
|
||||
* v1.7.0 — `/insights/walking-steadiness`.
|
||||
*
|
||||
* WALKING_STEADINESS sub-page. Reuses the generic HealthKitMetricPage scaffold;
|
||||
* the chart daily-aggregates through the rollup read path. Empty-state
|
||||
@@ -18,7 +18,7 @@ import { SubPageShell } from "@/components/insights/sub-page-shell";
|
||||
import { buildWeightBandsFromHeight } from "@/lib/analytics/value-bands";
|
||||
|
||||
/**
|
||||
* v1.4.25 W4 — `/insights/gewicht`.
|
||||
* v1.4.25 W4 — `/insights/weight`.
|
||||
*
|
||||
* Routed Weight sub-page. Renders the weight chart with the user's
|
||||
* height-derived green/orange/red bands plus the per-section AI
|
||||
@@ -87,7 +87,7 @@ export default function InsightsGewichtPage() {
|
||||
userTimezone={user?.timezone}
|
||||
/>
|
||||
|
||||
<MetricTargetSummary slug="gewicht" />
|
||||
<MetricTargetSummary slug="weight" />
|
||||
|
||||
<InsightStatusCard
|
||||
title={t("insights.assessmentTitle")}
|
||||
Reference in new issue
Block a user