Skip to content

Why the Flow web API (not AccessLink)

polar-flow-mcp drives the reverse-engineered Polar Flow web API (flow.polar.com) — the one the browser app uses — rather than Polar’s official AccessLink API. This page explains why, and what that choice implies.

The official Polar AccessLink API is read-only: it can list training history but cannot create or delete training targets. The whole point of this project — letting Claude schedule structured workouts in your diary — is impossible on AccessLink.

The web API at flow.polar.com — the one the Polar Flow browser app uses — supports the full set of mutating operations. So that is what this server targets.

The OpenAPI spec is maintained as a sibling repo, polar-openapi-maker, reverse-engineered from browser traffic. polar-flow-mcp:

  1. Vendors the spec under internal/flow/openapi.yaml.
  2. Generates a Go client from it with ogen.
  3. Wraps the client with the headless login chain, a cookie-jar with silent refresh, and the header/CSRF quirks the web API requires.

Every wire call is therefore type-checked Go generated from the spec, not hand-rolled HTTP. See Design decisions for the details of the wrapper and why each quirk exists.

Claude clientpolar-flow-mcpPolarMCP transport (stdio / HTTP)OAuth 2.1 AS (optional)MCP toolsFlow clientflow.polar.com (WAF)auth.polar.comogen client (generated)custom transport (uTLS + CSRF)cookie jar (chmod 600)login + silent refresh MCP JSON-RPC Bearer JWT (if public)session cookieHTTPSlogin / refresh

The dashed OAuth 2.1 Authorization Server is optional — it is off by default and only turns on when you set OAUTH_PUBLIC_URL to expose the server publicly. With it unset, /mcp has no inbound auth (run it on localhost or behind a trusted-network barrier).

CapabilityTool(s)
Confirm the linked accountget_user_info
Schedule a structured workoutcreate_training_target
List / read / edit / delete targetslist_training_targets, get_training_target, update_training_target, delete_training_target
Read the calendar & weekly totalsget_calendar_events, get_calendar_week_summary
Read completed sessionslist_training_sessions, get_training_session_summary, get_training_session_details
Aggregate progress over a rangeget_progress_summary
Log a manual sessioncreate_training_session

The write operations — creating, editing, and deleting targets, and logging manual sessions — are exactly the ones AccessLink cannot do. See the MCP tools reference for full argument schemas.

ComponentChoice
LanguageGo 1.26 (CGO disabled)
MCP servermark3labs/mcp-go (stdio + streamable HTTP)
OpenAPI clientogen-go/ogen
Spec sourcepolar-openapi-maker (vendored)
PersistencePlain JSON cookie jar (chmod 600)
ImageFROM scratch (~14 MB)