- To Strava in the feed
- 1 day
- Engineer on the integration
- 1
- Countries with members
- 58
- Platforms: iOS, Android and web
- 3
The problem
Their training was already being recorded. Just not by JustGains.
A run lives in Strava, a ride on a Garmin, a gym session in JustGains. Asking people to record everything twice is how you lose them.
One complete history
Every run, ride, swim and hike lands in JustGains automatically, next to the lifting.
Routes as a real feature
Not “you ran 8 km”, but the GPS line itself, to draw, share, replay and rank.
No duplicates
When a watch and the app record the same session, members see one activity with the best data from each.
The integration
One integration, every provider.
One engineer did it, from the first sync to a fork they now extend themselves.

- 01
Connect through Open Wearables
OAuth, tokens, provider quirks and webhook delivery were already solved, so the first provider was in the feed within a day.
- 02
Self-host it next to their stack
Their fork runs alongside the rest of their infrastructure, with Postgres, Redis and signed webhooks.
- 03
Wire it into their API
One service class holds all of it: activities arrive by webhook, with an hourly sync as a safety net, into one normalised record.
- 04
Reconcile and extend
Watch activities link to the gym workout they overlap, duplicates fold into one, and what the product needed next went into their fork.
What surprised them
The hard parts were already solved.
How quickly it became real
OAuth, tokens, provider quirks and webhook delivery were already solved.
How readable the codebase is
When they needed something new, they found the place and added it.
How little glue they needed
One service class and one webhook controller hold all of it.
In their words
“With Open Wearables we had Strava activities flowing into the JustGains feed in a day. When we needed route data it didn't return yet, we didn't wait on a vendor: we read the code, added it to our fork, and shipped. That is the difference open source makes.”
The deciding factor
Open source was the deciding factor.
Routes are the heart of their cardio product, and Open Wearables did not keep a Strava workout's route or name yet. With a closed aggregator that ends the conversation. They read the code and added it to their fork.
- Commits of their own
- 7
- Files changed
- 44
- Lines added
- 2,496
- Additions, all additive
- 4
Routes and names
Every synced workout keeps its GPS line and its title, not just its distance.

Instant webhooks
A five-line fix so workout.created fires straight away for a single new run.

Elevation profiles
Up to 300 points per activity, low and high preserved, with tests and docs.

Their deployment
Configs, a deploy script and a guide for the whole stack on their host.

The stack
One service class away from every device.
Providers
OAuth and provider webhooks. Strava is live; Garmin, Polar, Suunto, Oura, WHOOP and Fitbit run through the same pipeline.
Their Open Wearables fork
Self-hosted on Fly.io: API, Postgres and Redis, Svix webhooks, and their own additions for routes and elevation.
The JustGains API
.NET on Postgres. One service class is the only Open Wearables code; sync and reconciliation sit beside it.
The apps
iOS, Android and web: the activity feed, training history, routes, leaderboards and replays.
In the app
A synced run becomes a route.
Cardio recorded anywhere sits next to the lifting, and the GPS line becomes something members can open, run and compete on.
Synced from Strava
Route, distance, climb, pace and energy, with where it came from on every activity.


Becomes a route
Follow it, export GPX, race the leaderboard.


Replay
A flyover of an activity JustGains never recorded itself.




The result
Connect once. Then forget about it.
Connected Apps lists whatever their Open Wearables instance has enabled. A member taps a provider, approves it, and activities start arriving on their own: by webhook, with an hourly sync as a safety net.
Strava is live for all members today.
Activities, routes, heart rate, calories and elevation flow into the feed, history, routes and leaderboards. The other providers already run through the same pipeline and are turned on as each is verified.
What's next
Where they want to take it.
More providers
Garmin, Polar, Oura, WHOOP, Suunto and Fitbit already run through the same pipeline, turned on as each is verified.
Recovery into training
Sleep, HRV and readiness shaping what the workout engine suggests for the day.
Coaching
Coaches see a client's full picture, including what their watch recorded between sessions.
Contributing back
Upstreaming routes, names, elevation profiles and the webhook fix.
Build on top of it, not around it.
JustGains started from the public repository, forked it and shipped their own additions. Clone it and run it yourself, or see what it costs to have us stand it up inside your account.
FAQ
Questions this raises.
Did JustGains have to fork Open Wearables?
They chose to. Routes were missing for their product, so they added them to a fork with every change additive, and they merge upstream releases into it, most recently 0.6.3. They plan to contribute their additions back.
How do they stop the same workout appearing twice?
Their activity record is idempotent on the provider and its external id, and a reconciliation step links a watch activity to the gym workout it overlaps, folding cross-source duplicates into one.
Which providers are live?
Strava is live for all members. Garmin, Polar, Oura, WHOOP, Suunto and Fitbit already run through the same pipeline and are being turned on as each is verified.
