Headless API
Connect once. Stop writing a parser per vendor.
The same harmonisation layer the clinical product runs on, available on its own. Connect once, read one schema, and stop writing a parser per vendor. Access is granted per integration. There is no self-serve signup or public sandbox yet.
8
connected data sources
Apple Health, Oura, Whoop, Garmin, Fitbit, Polar, Google Fit, Strava
87
harmonised measures
Vitals, sleep, activity, body, cycle, glucose and 37 lab analytes
UCUM
units on every value
One dictionary, so two devices reporting the same thing stop being two things
Ingestion
From device to one schema.
- 01
Connect
OAuth per provider, or a signed device token for Apple Health.
Oura · Whoop · Garmin · Fitbit · Polar · Google Fit · Strava · Apple Health
- 02
Receive
Signed webhooks for push providers, scheduled reconciliation for the rest.
Signature verified · replay is a no-op
- 03
Archive
The raw payload is written to object storage before anything parses it.
Server-side encryption with KMS
- 04
Normalise
Each reading resolves to one of 84 measures and a UCUM unit.
Unknown unit rejected, never guessed
- 05
Derive
Daily features, then medians and spreads over each person's own window.
Workers drain every 15 minutes
- 06
Serve
One schema out, whether to the roster or to your own systems.
Scoped per care relationship
What harmonised actually means
Most integrations fail on the details rather than the transport. These are the four that cost the most to discover late.
One name per measurement
Heart rate variability measured as SDNN and as RMSSD are two different measurements, and stay two entries rather than being averaged into one number that means neither.
One unit per value
Every value carries a UCUM unit. Where a unit cannot be established the reading is rejected rather than guessed, because a silently wrong unit is worse than a gap.
Provenance on every row
Which device, which app, which version of the normaliser. Two sources reporting the same instant both survive; choosing between them is a decision you can see rather than one made during import.
Gaps stay gaps
Missing days are reported as missing. Nothing is interpolated to make a chart look continuous.
What a reading looks like
Every row is the same shape whichever device it came from, and carries enough provenance to answer where a number came from a year later.
Additional sources are added per integration. Ask about anything not listed.
{
"person_id": "9f2c…",
"concept": "hrv.sdnn",
"value": 58.4,
"unit": "ms",
"ts": "2026-09-15T05:12:00Z",
"local_date":"2026-09-15",
"source": { "provider": "oura", "device": "ring_gen3" },
"quality": { "coverage": 0.94 }
}Before you ask, three answers
- Where does the data sit?
- Raw payloads are stored immutably so a normalisation change can be replayed over history rather than losing it. Region is set per deployment.
- Is it certified?
- Not yet. We are pre-certification and will tell you exactly where we are on the call rather than showing a badge we have not earned.
- Can we self-serve?
- Not today. Access is granted per integration, which means a real conversation about your data before anything is wired up.
