feat(web): Phase 3b — medication/health/interactions feature UIs

Build the three core feature UIs on top of the now-wired stores + corrected API
client from Phase 3a, turning the runnable shell into a usable app.

Dashboard (pages/Dashboard.tsx): AppBar (Normogen + username + logout) over an
MUI Tabs container (Medications | Health | Interactions), widened to lg. User
loads on mount (needed for profile_id in medication create).

MedicationManager (components/medication/): full CRUD.
* List of medication cards (name, dosage·frequency, active chip, instructions)
  with edit/delete actions and an empty state.
* Create dialog: name/dosage/frequency/route(select)/instructions. profile_id
  sourced from user.profile_id with a 'default' fallback (TODO: real profiles).
  Payload typed to CreateMedicationRequest.
* Edit dialog (UpdateMedicationRequest shape) + delete confirm. Guards the
  optional medication_id field.

HealthStats (components/health/): trend cards + chart + add + table.
* Trend summary cards from /health-stats/trends (avg/min/max + trend arrow).
* recharts LineChart of a selected stat type over measured_at, with a type
  selector. Timestamp field is measured_at (not timestamp).
* Record dialog (stat_type/value/unit/measured_at/notes) + recent-readings table
  (date-fns formatted).

InteractionsChecker (components/interactions/): multi-select medication names
(chips) -> POST /interactions/check. Results rendered as cards with a
SeverityChip, description, and disclaimer. Success/empty states.

Shared SeverityChip (components/common/): maps InteractionSeverity ->
MUI Chip color (severe=error, moderate=warning, mild=success, unknown=default).

Added @mui/icons-material@7 (pinned to match @mui/material 7; npm tried to grab
v9 which needs material ^9).

Verified: npm run build clean (TS5 strict), dev server serves the app + all
component modules transform. Solaria round-trip confirmed every contract the UIs
call: medication create/list (200), interactions warfarin+aspirin -> severe,
health-stat create (201).
This commit is contained in:
goose 2026-06-28 04:31:16 -03:00
parent ef1bb9f4be
commit 1515923996
7 changed files with 886 additions and 60 deletions

View file

@ -0,0 +1,17 @@
import { Chip } from '@mui/material';
import { InteractionSeverity } from '../../types/api';
const CONFIG: Record<
InteractionSeverity,
{ color: 'error' | 'warning' | 'success' | 'default'; label: string }
> = {
[InteractionSeverity.Severe]: { color: 'error', label: 'Severe' },
[InteractionSeverity.Moderate]: { color: 'warning', label: 'Moderate' },
[InteractionSeverity.Mild]: { color: 'success', label: 'Mild' },
[InteractionSeverity.Unknown]: { color: 'default', label: 'Unknown' },
};
export const SeverityChip = ({ severity }: { severity: InteractionSeverity }) => {
const cfg = CONFIG[severity] ?? CONFIG[InteractionSeverity.Unknown];
return <Chip color={cfg.color} label={cfg.label} size="small" />;
};