June 5, 2026
Building an AI health coach
Building SyrupSync: one console for my health data
I got tired of bouncing between WHOOP, Apple Health, and a messy notes app every morning just to answer a simple question: should I train hard today, or back off?
That was the whole reason SyrupSync exists. Not because I wanted to build another wellness product. Because I was already wearing two devices, logging lifts and supplements by hand, and still couldn’t see one clean picture of a day. Recovery lived in one place. Steps and flights lived in another. Whether I hit protein and creatine lived in my head or a spreadsheet. By the time I pieced it together, the decision window was already gone.
So I built the thing I actually wanted to open.
What it is
SyrupSync is a personal health console. It takes WHOOP recovery and sleep, Apple Watch activity, and my own training and supplement logs, and fuses them into one record per day. Then it gives me a few ways to look at that record:
- Today for the morning brief and current state
- Log for the week’s training, feel, and supplements
- Trends for how things are moving
- Patterns for what moves with what
- Plan for goals and the next week
- Report for the weekly review
- Coach when I want to ask the data something directly
The tagline in the app is just “your health, consolidated.” That is basically the product.
It is live at syrup-sync.vercel.app.
Why I started
I train seriously. Strength work, cardio, protein targets, creatine, the usual. WHOOP is great at recovery physiology. Apple Watch is better at ambulatory stuff like steps and flights. Neither one knows what I actually lifted yesterday, how sore I felt, or whether I took my supplements. And neither one is good at answering, “given all of that, what should next week look like?”
I did not want five apps and a gut feel. I wanted one place that treated the day as the unit of truth.
I also wanted something honest about sources. If WHOOP and Apple both have HRV-ish signals, I want to see both, and I want clear rules about which one wins when they disagree. Manual training and subjective scores should always win for the things only I know. That sounds obvious until you try to model it.
How I actually use it
Most mornings I open Today. The first thing I see is the coach’s whiteboard: a short morning brief based on the day’s numbers, a recovery ring, and anything that looks off against my recent baseline. That is usually enough to decide whether today is a push day or a keep-it-easy day.
Then I sync WHOOP if I have not already. On mobile there is a sync button right in the header because I got sick of digging for it.
During the week I live in Log. It is a weekly grid for cardio sessions, lift groups, optional sets and RPE, and a quick feel score for energy, mood, soreness, and stress. Supplements are a tap checklist. There is also a month calendar that colors days by insight, which sounds minor until you are trying to spot a rough stretch without opening charts.
When something feels weird, I go to Trends or Patterns. Trends is the long view. Patterns is where I look at correlations, lagged predictors, and how often WHOOP and Apple even agree. That last one has saved me from overreacting to a single noisy metric more than once.
Plan is where I set goals, including peaking events with a target date. The coach gets that context and can talk about build vs taper instead of giving generic advice. Report is my end-of-week read: load, best and hardest days, zone work, and a written review.
And when I just want to ask, I use Coach. “Should I train hard today?” “Why has recovery been low?” “Am I overreaching this week?” Those are real questions I ask it.
The tech stack
Nothing exotic, chosen so I could ship and keep iterating:
- Next.js 14 (App Router) + React + TypeScript
- Tailwind for UI
- Recharts for charts
- Firebase Auth (Google sign-in) and Cloud Firestore for persistence
- Google Gemini (gemini-2.5-flash) for the coach, briefs, plans, and reports
- WHOOP Developer API for OAuth and live sync
- Client-side Apple Health export parsing (zip + XML)
- Hosted on Vercel, with a daily cron for optional morning agent checks
The app is intentionally resilient. No Firebase? It boots with 180 days of demo data. No Gemini key? It falls back to a rule-based coach. I wanted npm install && npm run dev to always work, even before any secrets were wired up. That made the early weeks much less painful.
The hard parts that matter
One row per day
The core idea is simple: users/{uid}/metrics/{YYYY-MM-DD} is the fused day. Training and supplements live nearby and mirror onto that record. Once you commit to “the day is the unit,” a lot of UI decisions get easier. So do AI prompts. The model is reading a coherent history instead of a pile of disconnected feeds.
Source hierarchy
WHOOP owns recovery and sleep physiology. Apple owns ambulatory activity. Manual always wins for training and subjective scores. Parallel Apple metrics still exist so I can compare devices instead of pretending one feed is complete. Getting that arbitration right took more thought than most of the charts.
Demo data that behaves like real physiology
Before OAuth worked, I needed every screen usable. So the demo dataset is deterministic and structured on purpose: sleep drives next-day recovery, strain affects soreness and recovery, stress suppresses HRV, and there are short illness windows that spike skin temp and respiratory rate. Fake flat random data would have made the correlations page look stupid. Building a synthetic history with real relationships made the product feel real much earlier.
Apple Health import
There is no live HealthKit sync yet. What I built is a real export importer: big zip, huge XML, streamed with a SAX parser so the browser does not melt. It is not glamorous, but it is the difference between “supports Apple Health” as a slide and “I can actually get my Watch data in.”
Insights off the main thread
Correlations, anomalies, and the heavier stats run in a web worker. Once you start computing lagged relationships and matrices over months of metrics, you feel every millisecond on the main thread. Moving that work out kept the UI usable.
From chat box to actual agent
The coach started as context-stuffed chat. That was useful, then not enough. I wanted it to investigate: pull ranges, check goals, look at training logs, compare metric pairs, and propose changes I could approve.
So I built an agent loop with tools. It can read summaries, metrics, insights, goals, workouts, and preferences. Writes go through propose-and-approve. If it wants to log something or set a goal, I see an action card first. That felt important. I do not want an AI quietly rewriting my training history.
There is also a proactive morning path. Optionally, a Vercel cron can sync WHOOP and nudge me if recovery is red, acute:chronic workload looks high, or something is multiple standard deviations off baseline. That turned the coach from something I only open when curious into something that can tap me on the shoulder.
How it grew
This was not a six-month roadmap with a launch party. It was roughly two intense weeks of building what I needed next.
First came the dashboard shell and demo data so the product existed. Then WHOOP OAuth and live sync, because without real recovery data it was just a prototype. Apple Health import came right after. Then the Log tab, because charts without a place to record training and supplements missed the point for me. Then better patterns views, source hierarchy, peaking goals, sets and RPE, the morning whiteboard brief. Then the autonomous coach with tools, approval, memory, and proactive runs.
A lot of the commit history is not glamorous feature work. It is OAuth callback failures, Firestore undefined fields, token refresh issues, UTC date-key bugs that shifted calendar days after evening logs, mobile nav fixes, caching the morning brief so I was not burning Gemini calls every refresh. That is what shipping a personal tool against real APIs looks like. You build the dream screen, then you spend the next day making Tuesday stop becoming Wednesday.
What I am proud of
I am proud that it is useful to me on a normal weekday, not just impressive in a README.
I am proud of the fusion model. Most “health dashboard” projects just chart whatever one API returns. The useful part here is making multiple sources feel like one record without lying about where each number came from.
I am proud that the logging UI matches how I actually train. Lift groups, quality taps, protein and creatine checkboxes, peaking events. That specificity is the opposite of a generic wellness template, and it is why I keep using it.
And I am proud of the human-in-the-loop agent. Tool use is cool. Letting it write freely to my health log would have been reckless. Approval cards were the right call.
What it is not
It is not a medical device. The privacy page says that plainly, and the coach is instructed the same way. Fitness and wellness only.
It is also unfinished in ways I am fine admitting. Apple data is export-based, not live HealthKit. The what-if simulator is linear association, not causation. Auth is Google-only. Some of the early docs still lag the product. I would rather keep building than pretend any of that is more polished than it is.
Why this felt worth building
I did not set out to make “an AI health platform.” I set out to stop arguing with three apps every morning.
Somewhere in the middle of wiring WHOOP tokens, parsing Apple exports, and teaching a coach to ask for approval before it logs a session, it stopped feeling like a side project and started feeling like infrastructure for my own training. That is the version I care about.
If you wear a recovery wearable, train on purpose, and have ever wished your data lived in one place with enough brains to help you decide what to do next, that is the itch SyrupSync scratches.
One console. One day at a time. Built because I needed it, then kept going because each missing piece became obvious the moment I tried to live in it.