django-strava
A reusable Django app for the Strava V3 API under the 2026 Developer Program,
backed by django-healthdatamodel:
activities land as Workout rows (with metadata) and, optionally, heart-rate /
cadence / power streams as Record series — nothing Strava-shaped is stored
except the OAuth connection itself.
Strava API notes (June 2026 Developer Program)
- Every new app lands in the Standard tier: 1 athlete by default, self-upgradeable to 10 in the API settings dashboard, no review needed. The developer account must hold an active Strava subscription.
- Rate limits (default): 200 requests/15 min & 2,000/day overall; 100/15 min &
1,000/day for reads. Doubled after the 10-athlete upgrade. The client retries
429s and exposes the latest
X-RateLimit-*headers. - The API host moves to a new domain in 2027 (available 2027-01-04, mandatory
2027-06-01). Set
STRAVA_API_BASE_URLto cut over without a code change. - Auth uses
Authorization: Bearerheaders and the newPOST /oauth/revokeendpoint exclusively — nothing here depends on the transports retired in 2027.
Quick start
-
Install alongside the storage layer:
pip install django-strava -
Add both apps to
INSTALLED_APPS:INSTALLED_APPS = [ ..., "healthdatamodel", "strava", ]
-
Configure credentials from your Strava API application:
STRAVA_CLIENT_ID = "..." STRAVA_CLIENT_SECRET = "..." STRAVA_REDIRECT_URI = "https://example.com/strava/callback/" # optional: STRAVA_CONNECT_SUCCESS_URL = "/" # default: /admin/ STRAVA_DEFAULT_SCOPES = ["read", "activity:read_all", "profile:read_all"] STRAVA_WEBHOOK_VERIFY_TOKEN = "..." # only if using webhooks STRAVA_API_BASE_URL = "https://www.strava.com/api/v3" # 2027 host cutover knob
-
Route the app and migrate:
path("strava/", include("strava.urls")),
python manage.py migrate -
Send a logged-in user to
/strava/connect/to run the OAuth flow, then sync:python manage.py sync_strava --user alice --days 30 python manage.py sync_strava --days 7 --streams --stream-limit 10
Webhooks
Route strava/webhook/ publicly, set STRAVA_WEBHOOK_VERIFY_TOKEN, then:
python manage.py create_strava_subscription https://example.com/strava/webhook/
Every event POST emits strava.signals.event_received; connect a receiver
that calls (or enqueues) strava.webhooks.process_event, which re-fetches the
activity through the authenticated API and ingests/deletes accordingly, and
marks connections disconnected on athlete deauthorization events.
Demo project
A click-through demo lives in demo/ (login → connect → sync → browse):
uv sync --group dev
export STRAVA_CLIENT_ID=... STRAVA_CLIENT_SECRET=...
uv run python manage.py migrate
uv run python manage.py createsuperuser
uv run python manage.py runserver
Set your Strava application's Authorization Callback Domain to localhost,
then open http://localhost:8000/.
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file django_strava-0.2.0.tar.gz.
File metadata
- Download URL: django_strava-0.2.0.tar.gz
- Upload date:
- Size: 20.5 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via:
twine/7.0.0 CPython/3.13.14
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
92dfe1fe3a1dd00a46d22a59d1b9e763ac1d285fad8c51b47e28ac9c3d5b64cf
|
|
| MD5 |
9917417fcd0663c3fb7b1b541700b2bc
|
|
| BLAKE2b-256 |
eeb7d3eec2beb3fa47f21232e4bd01c08ae029a692460a975a9a593d6a5709fd
|
Provenance
The following attestation bundles were made for django_strava-0.2.0.tar.gz:
Publisher:
ci.yml on django-health/django-strava
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
django_strava-0.2.0.tar.gz -
Subject digest:
92dfe1fe3a1dd00a46d22a59d1b9e763ac1d285fad8c51b47e28ac9c3d5b64cf - Sigstore transparency entry: 2336294882
- Sigstore integration time:
-
Permalink:
django-health/django-strava@223214b94e145fabacbf3f76fe0674a97594e519 -
Branch / Tag:
refs/tags/v0.2.0 - Owner: https://github.com/django-health
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
ci.yml@223214b94e145fabacbf3f76fe0674a97594e519 -
Trigger Event:
push
-
Statement type:
File details
Details for the file django_strava-0.2.0-py3-none-any.whl.
File metadata
- Download URL: django_strava-0.2.0-py3-none-any.whl
- Upload date:
- Size: 28.4 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via:
twine/7.0.0 CPython/3.13.14
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
fab80f10076beaaa521326e19da6e5a0b9c50d60a43c0b140386e309c9c3b61d
|
|
| MD5 |
cf59e6a7c746ae172b5ab1180fdc1543
|
|
| BLAKE2b-256 |
340ddf4f231d3a5d1a46e49173b8c13f718436b70da815e1a672ef51a41310bb
|
Provenance
The following attestation bundles were made for django_strava-0.2.0-py3-none-any.whl:
Publisher:
ci.yml on django-health/django-strava
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
django_strava-0.2.0-py3-none-any.whl -
Subject digest:
fab80f10076beaaa521326e19da6e5a0b9c50d60a43c0b140386e309c9c3b61d - Sigstore transparency entry: 2336294924
- Sigstore integration time:
-
Permalink:
django-health/django-strava@223214b94e145fabacbf3f76fe0674a97594e519 -
Branch / Tag:
refs/tags/v0.2.0 - Owner: https://github.com/django-health
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
ci.yml@223214b94e145fabacbf3f76fe0674a97594e519 -
Trigger Event:
push
-
Statement type: