Перейти к содержанию

Массовый импорт Strava

Документ описывает, как Grom импортирует тренировки из ZIP массового экспорта данных Strava.

Обзор

  1. Пользователь загружает ZIP экспорта Strava на странице Integration → Strava.
  2. Архив сохраняется в {storage.temp_dir}/{nickname}/.
  3. Сервер открывает ZIP через Go archive/zip и читает файлы напрямую (полной распаковки нет).
  4. Для каждой активности Grom создаёт YAML тренировки, при необходимости прикрепляет трек (AttachTrack), фото и снаряжение.
  5. После завершения временный каталог импорта пользователя удаляется.

Конфигурация

storage:
  temp_dir: tmp

По умолчанию: tmp (относительно бинарника grom, как storage.location).

Сопоставление колонок activities.csv

Номера колонок с 1. Strava локализует заголовки CSV; Grom всегда использует индексы.

Col Strava (пример RU) Поле Grom Примечания
1 ID физической активности external_id.id С external_id.name = strava; для детекта дубликатов
2 Дата тренировки start_date Разбор даты с учётом локали
3 Название тренировки name
4 Тип активности sport_type Сопоставление с ID типов спорта Grom
5 Описание description
6 Общее время duration_total_seconds Секунды
9 Относительное усилие relative_effort
10 Регулярный маршрут regular_track Boolean
12 Снаряжение equipment[] Поиск или создание
13 Название файла track GPX или .fit.gz в activities/
17 Время в движении duration_seconds Секунды
18 Дистанция distance Метры
19 Макс. скорость speed_max_kmh В CSV — м/с; Grom умножает на 3.6 → км/ч
20 Средняя скорость speed_avg_kmh В CSV — м/с; Grom умножает на 3.6 → км/ч
21 Набор высоты elevation_gain Метры
22 Высота спуска elevation_loss Метры
23 Высота низменности elevation_low Метры
24 Высота подъема elevation_high Метры
25 Макс. уклон grade_max
26 Средний угол уклона grade_avg
29 Макс. каденс cadence_max
30 Средний каденс cadence_avg
31 Макс. пульс heart_rate_max
32 Средний пульс heart_rate_avg
33 Макс. мощность watts_max Ватты
34 Средняя мощность watts_avg Ватты
35 Калории calories
36 Макс. температура temperature_max °C
37 Средняя температура temperature_avg °C
86 Всего шагов steps_total
93 Всего циклов cycles_total
101 Всего подходов sets_total
102 Общее количество повторений reps_total
103 Медиафайл media_files Фото из media/, видео игнорируются

Все новые поля YAML пишутся после distance и до track.

Игнорируемые колонки включают col 7 (локализованная дистанция в км) — вместо неё col 18 (метры).

Обработка трека: AttachTrack vs CreateWithTrack

Метод Сценарий Перезаписывает клиентские метрики
CreateWithTrack Ручной / multipart create с треком (включая Strava API sync) Нет — ненулевые клиентские start_date, длительности, distance, скорости и elevation сохраняются; трек заполняет только пустые поля
AttachTrack Импорт Strava ZIP Нет — значения CSV сохраняются

Оба пути пишут файл трека, задают device из FIT при наличии и генерируют map-preview.webp, если есть GPS-данные.

Снаряжение

В activities.csv (col 12) хранится отображаемое имя снаряжения, а в bikes.csv и shoes.csv части имени лежат в разных колонках (col 1 = прозвище, col 2 = марка, col 3 = модель). Колонка с прозвищем пуста, если у снаряжения нет своего названия, поэтому Grom сопоставляет все комбинации этих частей, а не только прозвище.

  1. Сопоставить имя снаряжения активности (col 12) с уже существующим снаряжением пользователя.
  2. Если не найдено — искать в bikes.csv → создать bike.
  3. Иначе искать в shoes.csv → создать shoes.
  4. Иначе создать снаряжение other с данным именем.

Снаряжение из bikes.csv / shoes.csv создаётся с именем-прозвищем (если оно пустое — марка модель), а также с маркой и моделью.

Определение локали

Grom определяет локаль экспорта по названиям типов спорта и строкам дат, затем разбирает:

  • Даты — английские и русские форматы Strava, включая четырёхбуквенные русские сокращения месяцев (сент., нояб., февр.).
  • Числа — десятичный разделитель запятая или точка, разделители тысяч.
  • Булевы — true / false (в экспортах Strava не зависят от локали).

Сопоставление типов спорта

Локализованные названия спорта Strava сопоставляются с ID типов спорта Grom (Run, Ride, WeightTraining, …). Когда Strava экспортирует общий тип вроде Workout / Тренировка, Grom может вывести более конкретный спорт из названия активности (например Пилатес (день) → Pilates). Неизвестные типы сводятся к Workout.

Результаты импорта включают:

  • parse_skipped — строки из activities.csv, которые не удалось разобрать (например неверные даты) и которые не импортированы
  • media_missing — пути фото из колонки media CSV, которых не было в ZIP (массовый экспорт Strava часто опускает старые медиа; видео игнорируются и не считаются)

API

Method Path Описание
POST /api/v1/integrations/strava/import Загрузка ZIP (поле archive), ответ 202
GET /api/v1/integrations/strava/import/status Прогресс загрузки/импорта

Повторный импорт

Если у пользователя уже есть тренировка с тем же external_id (name = strava и совпадающий id), активность пропускается.

Связанные материалы