mirror of
https://github.com/MBombeck/HealthLog.git
synced 2026-11-08 12:32:43 +00:00
The GLP-1 side-effect chips in the mood form write the localised label into the flat `MoodEntry.tags` column, and three readers matched that label against a hand-written list of English and German words: the therapy timeline, the Coach snapshot, and the doctor report's GLP-1 block. The app ships six locales. Tap the nausea chip with the UI in French, Spanish, Italian or Polish and the day never reached the timeline, the Coach grounded its answers on an empty side-effect list, and a clinician read an empty table over a record that had three months of symptoms. Nothing on any of those surfaces said the table was a filter rather than the truth. The three lists had also drifted apart from each other. The chips are a closed set with stable keys, so matching the label was the defect and the key is the fix. `glp1-side-effect-tags.ts` holds the catalogue — seven keys, each with the i18n key its chip renders — and the mood form now draws its strip from it, so the write side and the read side cannot diverge again. `glp1-side-effect-tag-match.ts` builds the label-to-key index by reading `messages/<locale>.json` for every entry in `locales`, rather than transcribing the labels into a second list. Transcribing would have fixed today's four locales and reopened the same hole on the day a seventh is added; deriving means a new bundle is matchable as soon as it lands, with no edit in the matcher. Comparison folds case, accents and separators, so the English and German tags already in the database keep resolving and a straight apostrophe matches the typographic one the French bundle uses. All three readers now report the catalogue key instead of the stored string. The same recorded symptom yields one key whatever language it was tagged in, which also fixes the mixed-language output an account gets after switching UI locale; the doctor-report PDF resolves the key through the label map so the clinician reads it in the report's language. A tag outside the catalogue is still never counted — a free-text mood tag must not reach a doctor as an invented symptom, and the rest of somebody's day does not belong on a therapy timeline. It is no longer dropped without trace: the timeline route annotates the unresolved count on its wide event, so the classification rate stays answerable while the tag text stays in the database. The Coach's copy of the list also carried `vomiting`, `reflux` and `erbrechen`. Those are removed. No chip writes them, so they only ever matched a hand-typed tag in two of six languages; keeping them would have rebuilt the defect inside its own fix. Restoring either symptom means giving it a chip and a label in all six bundles. The response schema for `GET /api/insights/glp1-timeline` now enumerates the keys, and its description no longer documents the bilingual match as if it were the contract.
docs/ — internal reference + operator playbooks
The user-facing documentation lives at https://docs.healthlog.dev — that's the canonical surface for self-hosting guides, integration walkthroughs, AI-provider setup, and the doctor-report workflow.
The files in this directory are the internal operator playbooks, audit notes, and machine-readable specs that ship alongside the source:
api/— the OpenAPI 3.1 spec for the native-client subset (iOS DTO codegen target). Seeapi/README.mdfor the preview commands. Also home to the MCP-server contract:api/mcp-capabilities.md(tools, resources, prompts, write model) andapi/mcp-skills.md(building a connector / skill).ops/— backup / restore + encryption-key-rotation playbooks. These are the runbooks an operator reaches for during an incident.self-hosting/— horizontal-scaling notes (HEALTHLOG_PROCESS_TYPE=web|worker|all) and the deploy-pipeline recipe. Routine install steps stay ondocs.healthlog.dev. Includesself-hosting/mcp.md— enabling the off-by-default MCP connector and pointing Claude.ai / ChatGPT / Claude Desktop at it, andself-hosting/sso.md— OIDC SSO login: IdP setup, the identity-pinning security model,OIDC_ONLYconsequences, and the break-glass runbook. Alsoself-hosting/geolite2.md— bringing your own offline GeoLite2 databases viaGEOLITE2_DIRinstead of sending login IPs to a third-party lookup. Andself-hosting/account-sharing.md— letting one account on the instance open another's health record: the three access levels, the eight sections a grant can be narrowed to, managed profiles for somebody with no login and the guardians who look after them, what revocation does and does not undo, and which trust properties of the instance are unchanged by any of it.migration/— release-by-release migration notes. Read the entry for the version you're upgrading from.audit/— per-release audit summaries archived for forensic traceability.apple-store-connect-checklist.md— the iOS submission gate.doctor-report.md— PDF generator design notes.codex-protocol-spec.md— Codex / ChatGPT OAuth protocol reverse-engineering notes.ui-guidelines.md— UI / a11y house style.
If you're a self-hoster looking to spin up an instance, start at https://docs.healthlog.dev or jump to the Quick Start in the project README.