trainingload
Training-load metrics and Strava archive parsing for endurance sport — with zero runtime dependencies.
trainingload is a small, typed Python toolkit for the math behind endurance
training analytics: Training Stress Score (TSS) for swim/bike/run/strength, the
Performance Management Chart (CTL / ATL / TSB), and a parser for Strava's bulk
data export. It's the load engine extracted from the production codebase of
Motus — an AI triathlon coach — and packaged so you
can drop it into a notebook, a script, or your own app.
No NumPy, no pandas, no web framework. Just the standard library.
Install
pip install trainingload
Requires Python 3.10+.
Quick start
from datetime import date
from trainingload import calculate_pmc
# Daily Training Stress Score -> fitness (CTL), fatigue (ATL), form (TSB)
series = calculate_pmc({
date(2026, 1, 1): 80.0,
date(2026, 1, 2): 120.0,
date(2026, 1, 3): 0.0, # rest day
})
today = series[-1]
print(today.ctl, today.atl, today.tsb)
What's inside
Three independent modules — use one or all three.
1. trainingload.tss — Training Stress Score
Sport-aware TSS from whatever data you have (power, pace, heart rate, or just duration), with sensible fallbacks.
from trainingload import TSSCalculator, TrainingZones
zones = TrainingZones(bike_ftp=250, run_threshold_pace=300, swim_css=95)
# Cycling from normalized power:
TSSCalculator.calculate_bike_tss(duration_seconds=3600, normalized_power=200, ftp=250) # 64.0
# Or let it pick the best method for the sport and data available:
TSSCalculator.estimate_tss(sport_type="run", duration_seconds=3600,
distance_meters=10000, zones=zones) # 69.4
# Show your work — which method, inputs and formula were used:
TSSCalculator.explain_tss_calculation(sport_type="bike", duration_seconds=3600,
tss=64.0, normalized_power=200, zones=zones)
2. trainingload.pmc — Performance Management Chart
CTL/ATL/TSB time series and a current-fitness snapshot from a map of daily TSS.
from datetime import date
from trainingload import fitness_summary, interpret_tsb, recommend_training
summary = fitness_summary(daily_tss) # {date: tss} -> ctl/atl/tsb + ramp rate
print(interpret_tsb(summary.tsb)) # e.g. "fresh"
print(recommend_training(summary.tsb, target_event_days=7))
- CTL (Chronic Training Load) — 42-day EMA of TSS → fitness
- ATL (Acute Training Load) — 7-day EMA of TSS → fatigue
- TSB (Training Stress Balance) — CTL − ATL → form
3. trainingload.strava — bulk-export parser
Turn the activities.csv from a Strava data export into typed records. Accepts
a file path or an in-memory stream (e.g. an upload), so it works server-side
or in a worker without touching disk.
from trainingload import StravaArchiveParser
parser = StravaArchiveParser()
activities = parser.parse_zip_activities("strava_export.zip")
meta = parser.parse_zip("strava_export.zip") # totals, date range, sport breakdown
End-to-end: Strava export → fitness curve
See examples/strava_to_pmc.py for the full flow —
parse the archive, score every activity, and print your current CTL/ATL/TSB:
python examples/strava_to_pmc.py path/to/strava_export.zip
Accuracy & credits
TSS, NP/IF, and the CTL/ATL/TSB model come from the endurance-training literature popularised by Hunter Allen & Andrew Coggan (Training and Racing with a Power Meter) and the TrainingPeaks Performance Management Chart. The implementations here are independent and intentionally transparent — every formula is documented in the source and covered by tests.
Trademark note. "TSS", "CTL", "ATL", "TSB", "NP" and "IF" are used in this project descriptively to refer to widely-documented training-load concepts. They are trademarks of Peaksware, LLC (TrainingPeaks). This project is not affiliated with, sponsored by, or endorsed by TrainingPeaks or Strava.
Built by Motus
trainingload powers the analytics inside Motus,
an AI coach for runners and triathletes. If you want the metrics in this library
turned into adaptive training plans, race predictions and a coach in your pocket,
give Motus a try
— and read the training-science guides on the Motus blog.
Contributing
Issues and pull requests are welcome — see CONTRIBUTING.md.
License
MIT © Motus
Release files for trainingload 0.1.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| trainingload-0.1.0.tar.gz | 23.5 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| trainingload-0.1.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 40.9 kB
Release files / trainingload-0.1.0.tar.gz
| Download URL | trainingload-0.1.0.tar.gz |
|---|---|
| Size | 23.5 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
2d1e50111b27b21593343791d3e4bc13147e549a62edaf28eaa5e658cfab271b
|
|
BLAKE2b-256 checksum How to use checksums |
4b61ebf40dc5603f994bf647f58bbcc72c321b15c1ece4af61e99c79893357ce
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.13.12
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Jun 6, 2026.
Transparency logRelease files / trainingload-0.1.0-py3-none-any.whl
| Download URL | trainingload-0.1.0-py3-none-any.whl |
|---|---|
| Size | 17.4 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
60bc5eabe9c92924bbb10b0a2f0b9da23245de5dcc39fddeb3e851d7a0c0f703
|
|
BLAKE2b-256 checksum How to use checksums |
fb8170cba1ca1d28441b8fd7b5df9942eb0533742f3dc24512f6123e89c3ca53
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.13.12
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Jun 6, 2026.
Transparency log