Repository navigation
Email Notifications
Three optional email features are built in. All are no-ops when not configured.
Sends a plain-text warning or alert when a tracked bike part crosses a service threshold. Runs as part of the nightly strava-my-activities cron job. Settings go in /etc/strava-my-activities.conf.
# /etc/strava-my-activities.conf
# Recipient(s) — comma-separated. Leave empty to disable.
STRAVA_MY_BIKE_EMAIL="you@example.com"
# SMTP settings (same format as the leaderboard email below)
STRAVA_EMAIL_SMTP="smtps://smtp.gmail.com:465"
STRAVA_EMAIL_USER="your.address@gmail.com:xxxx-xxxx-xxxx-xxxx"
STRAVA_EMAIL_FROM="your.address@gmail.com" # optional, defaults to STRAVA_EMAIL_USERAfter setting STRAVA_MY_BIKE_EMAIL, open bike.html in your browser, click Edit on any part, and tick "Email alert when service threshold is reached". The checkbox only appears when the email address is configured.
| Threshold % | Subject prefix | Frequency |
|---|---|---|
| ≥ 90 % | [WARNING] |
Once per threshold crossing |
| ≥ 100 % | [ALERT] |
Once on crossing; re-sends every 7 days while still overdue |
Each email lists all affected parts with their current %, ridden km, riding hours, and days since last service.
Alert state is stored in $STATE_DIR/bike-email-state.json. When a part is serviced and drops back below 90 %, its tier resets automatically — you'll receive a fresh warning the next time the threshold is approached.
On the 1st of each month at 08:00, /usr/bin/strava-email-monthly sends a plain-text leaderboard for the previous month (one section per club) to every address in STRAVA_EMAIL_TO. Each address receives a separate email. Settings go in /etc/strava-leaderboard.conf.
# /etc/strava-leaderboard.conf
STRAVA_EMAIL_SMTP="smtps://smtp.gmail.com:465"
STRAVA_EMAIL_USER="your.address@gmail.com:xxxx-xxxx-xxxx-xxxx" # Gmail App Password
STRAVA_EMAIL_FROM="your.address@gmail.com" # must match the Gmail account
STRAVA_EMAIL_TO="alice@example.com,bob@example.com"- Enable 2-Step Verification on your Google account
- Go to https://myaccount.google.com/apppasswords
- Generate an App Password for "Mail" / "Other"
- Use the 16-character password in
STRAVA_EMAIL_USER(format:email:apppassword)
The From: address must match the authenticated Gmail account — Gmail rejects mail whose From: differs from the logged-in user.
STRAVA_EMAIL_TEST_MONTH=2026-07 /usr/bin/strava-email-monthlyReplace 2026-07 with any YYYY-MM value to send the leaderboard for that month.
Leaderboard dates are first-seen dates in API mode (approximate) and real activity dates in scrape mode. The monthly filter uses whatever date is stored in the NDJSON activity store.
Athletes whose total distance for the period is zero are excluded from the leaderboard tables (monthly, weekly, and yearly top-5). This drops indoor/distance-less rides (e.g. spinning, yoga) that would otherwise appear as empty 0.0 km rows on a distance board. An athlete who also recorded a real outdoor ride still appears, and their indoor time is still summed into their total.
/usr/bin/strava-email-weekly sends a combined leaderboard showing the current month totals plus a "last week" column. Scheduled by cron; the last-week window is always auto-computed from today.
# Send weekly email with August month leaderboard + last-week column
STRAVA_WEEKLY_TEST_MONTH=2026-08 /usr/bin/strava-email-weekly/usr/bin/strava-email-yearly fires once a year on 1 January at 09:00 and sends a year-in-review for the just-ended year. It covers every configured club and includes:
- Club totals — km, activities, elevation, unique athletes, avg km/h for the full year
- Top 5 athletes — ranked by total distance for the year
- Single-activity highlights — fastest (km/h), longest (km), and most elevation (m) across all clubs
Add STRAVA_EMAIL_YEARLY_TO to /etc/strava-leaderboard.conf. Falls back to STRAVA_EMAIL_TO if not set.
# /etc/strava-leaderboard.conf
STRAVA_EMAIL_YEARLY_TO="alice@example.com,bob@example.com"STRAVA_EMAIL_SMTP, STRAVA_EMAIL_USER, and STRAVA_EMAIL_FROM must also be set (same as the monthly email).
STRAVA_EMAIL_TEST_YEAR=2025 /usr/bin/strava-email-yearlyscp strava-email-monthly.sh root@192.168.1.1:/usr/bin/strava-email-yearly `
&& ssh root@192.168.1.1 "chmod 0755 /usr/bin/strava-email-yearly"install.sh installs this automatically and adds the cron entry (0 9 1 1 *).
All three nightly scripts are wrapped by /usr/bin/strava-cron-guard. When any of them exits non-zero, the guard sends an alert to every address in STRAVA_EMAIL_ALERTS_TO, with the script name, exit code, and the last 50 lines of output in the email body. Uses the same SMTP settings as above.
# /etc/strava-leaderboard.conf
STRAVA_EMAIL_ALERTS_TO="admin@example.com,ops@example.com"STRAVA_EMAIL_SMTP, STRAVA_EMAIL_USER, and STRAVA_EMAIL_FROM must also be set.
strava-cron-guard falseRuns /usr/bin/false (exits 1) and triggers the alert if SMTP is configured.
The guard is already wired into the cron lines installed by install.sh:
50 23 * * * /usr/bin/strava-cron-guard strava-leaderboard >> /var/log/strava-leaderboard.log 2>&1
55 23 * * * /usr/bin/strava-cron-guard strava-my-activities >> /var/log/strava-my-activities.log 2>&1
0 8 1 * * /usr/bin/strava-email-monthly >> /var/log/strava-email-monthly.log 2>&1
0 8 * * 1 /usr/bin/strava-email-weekly >> /var/log/strava-email-weekly.log 2>&1
0 9 1 1 * /usr/bin/strava-email-yearly >> /var/log/strava-email-yearly.log 2>&1
scp strava-cron-guard.sh root@192.168.1.1:/usr/bin/strava-cron-guard `
&& scp strava-email-monthly.sh root@192.168.1.1:/usr/bin/strava-email-monthly `
&& scp strava-email-monthly.sh root@192.168.1.1:/usr/bin/strava-email-weekly `
&& scp strava-email-monthly.sh root@192.168.1.1:/usr/bin/strava-email-yearly `
&& ssh root@192.168.1.1 "chmod 0755 /usr/bin/strava-cron-guard /usr/bin/strava-email-monthly /usr/bin/strava-email-weekly /usr/bin/strava-email-yearly"