← Back to Projects
DDL Case Study · Governance Architecture

HealthStack

Personal health intelligence — encrypted local-first observation capture, governed AI output envelope, sensitivity-tiered data sovereignty. Your data does not leave your machine without your explicit opt-in.

Problem

Personal health data lives in a dozen disconnected portals — one for labs, one for prescriptions, one for the hospital stay from three years ago. No longitudinal record. No privacy controls. No ability to correlate a lab trend with a medication change made six weeks prior.

Approach

A local-first, encrypted SQLite stack. Every observation is a governed fact row with a single registry entry. AI can observe and propose — never silently write. Sensitivity tiers determine what can leave the device. Context at the time of capture is preserved permanently.

Deliverable

Observation registry schema with five fact tables, AI output envelope standard, build toolchain with encrypted migration support, DuckDB analytics attach layer, and a capture model with a 30-second ceiling and save-first invariant.

Observation Registry · Recent Entries
IDFact TableValueObservedSensitivityStatus
OBS-0041Fact_LabResulteGFR 872026-07-15 08:12SENSITIVERATIFIED
OBS-0042Fact_SymptomFatigue — moderate2026-07-16 14:30STANDARDCAPTURED
OBS-0043Fact_MedicationEventLisinopril 10mg — taken2026-07-17 07:01SENSITIVECAPTURED
OBS-0044Fact_VitalBP 122/78 · HR 642026-07-17 07:05STANDARDCAPTURED
OBS-0045Fact_LabResultHbA1c 5.6%2026-07-18 09:00SENSITIVEPENDING_RATIFICATION
CAPTURED 38
RATIFIED 17
PENDING 4
SUPERSEDED 2
61 total observations · page 1 of 13
AI Output Envelope

Every AI output carries exactly one of three postures. No escape hatch. No unsolicited writes. Sensitivity inherits from the source observations. Confidence is derived from evidence count — never model-supplied.

OBSERVATION

Raw captured fact. Immutable once saved. Source and timestamp are the authority.

BP 122/78 · HR 64 — captured 2026-07-17 07:05 · Home monitor
INFERENCE

Pattern derived from two or more observations. Confidence is evidence-count, never model-supplied.

Blood pressure has trended downward over 14 days (4 observations). Confidence: LOW.
PROPOSAL

Ratifiable action or data row proposed by the AI extractor. Requires explicit human acceptance before writing.

Propose adding OBS-0046: Lisinopril — taken 2026-07-19 07:03 based on reported pattern.
Sensitivity Tiers
STANDARD
Exported freely. No restriction on sharing class.
SENSITIVE
Protected export only. Opt-in per destination. Includes medications, diagnoses, labs.
HIGHLY_SENSITIVE
Device-only. Never leaves the encrypted store. Mental health, reproductive, psychiatric data.
Schema · Table Map
observation_registry
Single referent for every observation across all fact tables. FK anchor.
Fact_LabResult
Lab values with reference ranges, ordering provider, and ratification state.
Fact_Symptom
Self-reported symptoms with severity, body site, and duration.
Fact_MedicationEvent
Dose events with scheduled offset, adherence flag, and supersession chain.
Fact_Vital
Point-in-time vitals: BP, HR, SpO2, temp, weight.
Bridge_ObservationContext
Captures context at time of observation: sleep, stress, fasting, activity.
Dim_ClinicalAnchor
Optional link to condition, episode, or care encounter.
Design Invariants
INV-001Save-first

Numbers commit before context is written. Context that gates a write eventually stops logging.

INV-00230-second ceiling

Capture must complete in under 30 seconds. Only timestamp and one value are required.

INV-003Append-only

Observations are never edited in place. Corrections forward through new events — source is immutable.

INV-004No silent writes

AI cannot write to the registry. Every proposed row requires explicit human acceptance.

INV-005Sensitivity inherits

A derived fact inherits the highest sensitivity class of its source observations — no downgrade.

INV-006DuckDB READ_ONLY

Analytics attach is read-only enforced. A write through DuckDB would bypass every trigger invariant.

ARCHITECTURE NOTE

SQLite was chosen over DuckDB as the write engine for one reason: triggers. Engine-enforced invariants — append-only, status transition validation, FK integrity across fact tables — are not available in DuckDB. DuckDB attaches the same file as READ_ONLY for analytics. The separation is load-bearing: it means the analytics layer can never bypass the write-path invariants, no matter how it is queried.

HealthStack · v0.1 · Local-First Personal Health Intelligence · Built by DDL · 2026