diff --git a/API.md b/API.md index b02d8e5..f5d614c 100644 --- a/API.md +++ b/API.md @@ -1,3 +1,72 @@ + +
+Отличная задача! Я обновил вашу документацию, интегрировав в неё рабочие примеры кода на Python (основанные на вашем тестовом скрипте) и добавил реальные примеры JSON-ответов с детальной расшифровкой каждого поля. Это сделает API кристально понятным для фронтендеров и интеграторов.
Ниже представлена готовая обновленная версия документации.
Базовый URL:
https://ex.neimarker.ru/api/Формат дат: ISO 8601 (например,
2026-04-20T15:30:00Z)Аутентификация (Для интеграций): Заголовок
Authorization: Api-Key <токен>Аутентификация (Web): Заголовок
Authorization: Bearer <jwt_access_token>
<a name="auth"></a>
В системе предусмотрено два типа доступа: для живых пользователей (через веб-интерфейс с логином/паролем) и для сторонних систем (интеграция по статичному API-ключу).
⚠️ Важно: Для получения ключа интеграции (
Api-Key) вашей организации необходимо обратиться в службу технической поддержки или к менеджеру.
import requests
+
+BASE_URL = "https://ex.neimarker.ru/api/"
+API_KEY = "ВАШ_УНИКАЛЬНЫЙ_ТОКЕН_ИНТЕГРАЦИИ"
+
+headers = {
+ "Authorization": f"Api-Key {API_KEY}"
+}
+<a name="devices_crud"></a>
Автоматически ограничивает выдачу только устройствами, принадлежащими организации, чей токен совершает запрос.
+Метод | Эндпоинт | Описание +-- | -- | -- +GET | /devices/ | Список всех устройств организации. +POST | /devices/ | Создание устройства. Ожидает: name, bucket_volume. MAC и API-токен генерируются автоматически. +GET | /devices/# Получаем часовые отрезки (папки)
+folders = requests.get(f"{BASE_URL}devices/43/folders/", headers=headers).json()
+folder_id = folders[0]['id']
+
+# Получаем Bounding Boxes для конкретного отрезка видео
+detections = requests.get(f"{BASE_URL}devices/43/folders/{folder_id}/detections/", headers=headers).json()
+Пример ответа /folders/:
[
+ {
+ "id": 5495,
+ "process_after": "2026-04-23T15:02:00+03:00",
+ "received_at": "2026-04-23T15:18:28.541403+03:00",
+ "video_file": "/media/devices/43/2026/04/23/15/video_7d4b6624.mp4",
+ "file_count": 4350,
+ "original_width": 480,
+ "original_height": 640
+ }
+]
+Интерпретация:
process_after: Временная метка начала данного часового отрезка.
video_file: Относительный путь до сшитого файла mp4.
file_count: Количество исходных кадров, вошедших в это видео (используется для расчета реального FPS).
Пример ответа /detections/:
{
+ "1": [
+ ["u00003", 0.3593, 0.2955, 0.5738, 0.5464, 0.97, null]
+ ],
+ "2": [
+ ["u00003", 0.3579, 0.2975, 0.5685, 0.5471, 0.97, null]
+ ]
+}
+Интерпретация:
Ключи словаря ("1", "2") — это номера кадров (фреймов) в видеофайле.
Значения — массив детекций. Формат: [class_name, x_min, y_min, x_max, y_max, confidence, tracking_id].
Координаты x и y нормализованы от 0.0 до 1.0. Для отрисовки на канвасе их нужно умножить на ширину и высоту видеоплеера.
# Запрос GPS трека за период
+traj_params = {"start_date": start_date, "end_date": end_date}
+trajectory = requests.get(f"{BASE_URL}devices/43/trajectory/", headers=headers, params=traj_params).json()
+
+# Запрос точного видео-кадра на конкретное время
+frame_params = {"timestamp": "2026-04-23T12:00:00Z"}
+video_frame = requests.get(f"{BASE_URL}devices/43/video-frame/", headers=headers, params=frame_params).json()
+Пример ответа /trajectory/:
[
+ { "ts": "2026-04-23T03:17:00.796000Z", "lat": 56.2350, "lon": 43.6361 },
+ { "ts": "2026-04-23T03:18:00.997000Z", "lat": 56.2350, "lon": 43.6361 }
+]
+(Массив точек с координатами широты lat и долготы lon и временной меткой ts для рендеринга полилинии на картах Yandex/Google/Leaflet).
Пример ответа /video-frame/:
{
+ "video_url": "http://ex.neimarker.ru/media/devices/43/.../video_7d4b6624.mp4",
+ "seek_seconds": 182.875,
+ "folder_id": 5495,
+ "frame_index": 4389,
+ "debug_fps": 24.0
+}
+Интерпретация:
Этот эндпоинт позволяет кликнуть на график аналитики или на карту, и мгновенно найти нужное место в видеоархиве.
video_url: Ссылка на нужный часовой отрезок видео.
seek_seconds: Точное время в секундах, на которое нужно перемотать HTML5 video плеер (video.currentTime = 182.875).