Developers
The Lifterclub API lets your app read and write a user's workout log, with their permission. It's the same log their AI assistant and the Lifterclub app use.
Start here
- Quickstarts for TypeScript, Go, an assistant over MCP, and matching exercise names, each runnable in a few minutes.
- An example app, open source: signing a person in, logging, mirroring the log and receiving webhooks.
- The API reference for the routes every Open Workout server serves. Lifterclub serves them, plus parsing, matching, records, profiles, routines, programs and imports.
The basics
- Base URL:
https://lc-do-api.runmighty.dev - Authorization: OAuth 2.1, the authorization code flow with PKCE (
S256). There are no API keys for apps. - Discovery: any endpoint answers an unauthenticated request with
401and aWWW-Authenticateheader naming the protected resource metadata, which names the authorization server. - Workouts are Open Workout Schema v0 documents, and exercises are identified by Open Exercise IDs.
- Errors are RFC 9457
application/problem+json. Creates take anIdempotency-Keyheader, and a workout'sexternal_id(your own ID for it) never logs twice.
The sandbox
Build against the sandbox: the API at https://lifterclub-api.runmighty.dev, MCP at https://lifterclub-mcp.runmighty.dev and the app at lifterclub.runmighty.dev. Sign in with your own Google account to make a test account; nobody needs to set you up.
It runs unreleased code, and its data may be reset at any time, so use test data only. Move to the base URL above once your app works.
Registering your app
- Use a client ID metadata document: an
https://address on your own domain serving your app's name and redirect URIs, which you use as yourclient_id. It proves your domain, so your app's writes carry its plain name, and it's what verification asks for. - Or register at
/oauth/register(RFC 7591). Anyone can, so the consent page says we haven't checked the app, and its writes carryunverified-before its name. - Ask for the scopes your app uses, and read the granted ones from the token response: the person may grant less.
workouts:read See workouts, progress and personal records
workouts:write Add, change and delete workouts
profile:read See the profile: name, units, goals and equipment
profile:write Change the profile
meals:read See meals and the foods the person added
meals:write Add and change meals and the person's own foods
programs:read See training programs
programs:write Create and change training programs
Matching exercise names
POST /v1/match maps up to 50 names to Open Exercise IDs, each as a sure match, a close one to confirm with your user, or unmatched with candidates. It needs no person: a confidential app takes a token of its own with the client credentials grant, which carries only catalogue:match. It uses the shared catalogue only and stores nothing, and a call counts once against your app's read budget.
curl https://lc-do-api.runmighty.dev/oauth/token -u "$CLIENT_ID:$CLIENT_SECRET" \
-d grant_type=client_credentials
curl https://lc-do-api.runmighty.dev/v1/match -H "Authorization: Bearer $TOKEN" \
-H 'Content-Type: application/json' -d '{"names": ["db bench", "rdl"]}'Reading what people write
POST /v1/parse turns a sentence like "bench 3x8 at 185" into a draft workout without saving it, and POST /v1/workouts/from-text saves one. Both act for a person who has allowed Lifterclub to store their workout data, with workouts:write.
A model reads the text and every number is checked against it. Each person gets 500 sentences a day, and your app 5,000 across all its users (ten times that once verified). Past either, the request still succeeds: a simpler reader answers, and warnings says llm_limited.
Meals and foods
Meals are Open Food Log v0 documents, under /v1/meals with meals:read and meals:write. An item names a food by ID, or in the person's words, which are matched for you: a close or unmatched food isn't counted until the person confirms it. GET /v1/foods searches the food catalogue, and POST /v1/meals/parse turns a sentence, or a meal photo, into a draft meal without saving it: whatever a photo supplies is marked as an estimate.
An amount the person didn't give is assumed to be the food's default portion and listed in estimates. When the person has asked not to see numbers, responses leave totals out. GET /v1/meals?updated_since= is the change feed, and webhooks send meal.created, meal.updated and meal.deleted.
AI agents (A2A)
Another AI agent can hand meals to Lifterclub's nutrition agent over A2A: send what the person ate, in their words or as an Open Food Log meal, and get the logged meal back. Its card is at https://lc-do-mcp.runmighty.dev/.well-known/agent-card.json; it signs in with the same OAuth flow, for the agent's URL with meals:read and meals:write. Its skills are log-meal, food-lookup, get-meals, nutrition-summary and targets, and log-meal-photo reads a photo as estimates. A food it isn't sure of leaves the task waiting for input, with candidates to confirm on the same task.
Rules for apps and assistants
- Log only what the person said. Mark anything you inferred, from a photo or a screen, as estimated.
- When a result lists
needs_confirmation, ask the person which exercise they meant; never guess. - Show the person the
summary, and anywarnings. - If the person has asked not to see numbers, don't volunteer records, totals or progress.
- Wait out
Retry-Afteronrate_limited.
We check these before verifying an app.
Open standards
The formats are published on their own, under open licences, so your app can use them without Lifterclub.
- Open Workout Schema: a workout log, and a program, as JSON Schema. Apache-2.0.
- The MCP tool profile: the tools an assistant uses over a log, as this server lists them.
- Open Food Log: a food, a meal and a food log as JSON Schema, with a nutrient vocabulary. Apache-2.0, and CC0 for its food catalogue. A draft, and newer than the others.
- Open Exercise: the exercise catalogue and its schema. CC-BY-SA 4.0 for the catalogue.
- Conformance checks for a server of your own, which Lifterclub passes.
Limits and partners
- Each account gets 600 reads and 60 writes a minute, shared by everything connected to it. Each app also has a budget across all its users: 1,200 reads and 120 writes a minute, ten times that once we've verified it.
- Once your app works, ask us to verify it: we check who runs it and what it does with the log. A verified partner gets ten times the app budget and a listing on the Connect page.
Clients
Two thin clients send your token, add an Idempotency-Key to every create, turn errors into values you can branch on, and page through workouts and the change feed for you. Both are open source in openexercise/open-workout.
npm install @openexercise/open-workout-client
go get github.com/openexercise/open-workout/clients/goA first call
curl https://lc-do-api.runmighty.dev/v1/workouts \
-H "Authorization: Bearer $TOKEN"