Read-only доступ к данным о политических преследованиях в России
API предоставляет структурированный доступ к данным о политических преследованиях в России. Данные обновляются несколько раз в сутки.
Это экспериментальный API — структура эндпоинтов и набор полей могут меняться.
Базовый URL: https://api-data.ovd.info · Swagger UI: /docs
Все запросы (кроме GET /datasets) требуют заголовок:
X-API-Key: <ваш_ключ>
Для получения ключа обратитесь к команде ОВД-Инфо по адресу [email protected]. Ключ выдаётся один раз — сохраните его.
| Метод | Путь | Описание | Ключ |
|---|---|---|---|
| GET | /datasets | Схема датасетов: колонки, фильтры | Нет |
| GET | /persons | Список персон с фильтрацией и поиском | Да |
| GET | /persons/{id} | Персона по UUID | Да |
| GET | /organisations | Список организаций | Да |
| GET | /organisations/{id} | Организация по UUID | Да |
| GET | /pp_persecutions | Политические преследования | Да |
| GET | /profiles | Карточки персон (адрес для писем, «Весточка», имя/история/статус) | Да |
| GET | /profiles/{id} | Карточка персоны по id (?subset=full — + уголовные дела, реестры, оценки правозащитников, хронология событий одним ответом) | Да |
| Параметр | Тип | Описание |
|---|---|---|
limit | int | Строк в ответе (по умолчанию 100, макс. 1000) |
offset | int | Смещение для пагинации. Ответ содержит total — общее число строк с учётом фильтров. Взаимоисключим с cursor |
cursor | str | Значение next_cursor из предыдущего ответа — устойчивая keyset-пагинация без дублей/пропусков при обходе больших списков (в отличие от offset, не зависит от того, есть ли в данных повторяющиеся значения sort-колонки, например updated_at у пачки записей одного импорта). Переопределяет sort/order значениями, с которыми был выпущен — см. «Пагинация» ниже |
q | str | Поиск подстроки по всем search-полям одновременно |
{col} | str | Точный фильтр по filter-полю. Поддерживает операторы — см. ниже |
subset | str | Подмножество колонок: rfm или inoteka — подробнее ниже |
sort | str | Имя колонки для сортировки. Только колонки, входящие в текущий ответ |
order | str | asc (по умолчанию) или desc |
timeline | bool | Только /persons/{id} — добавляет persecutions[] с преследованиями |
Все filter-поля поддерживают расширенные операторы через суффикс __{оператор}:
| Синтаксис | Оператор | Пример |
|---|---|---|
?{col}=val | Точное совпадение | ?persecution_status=Осуждён |
?{col}__gt=val | Больше чем | ?start_year__gt=2021 |
?{col}__gte=val | Больше или равно | ?updated_at__gte=2026-08-01 |
?{col}__lt=val | Меньше чем | ?verdict_date__lt=2024-01-01 |
?{col}__lte=val | Меньше или равно | ?verdict_date__lte=2023-12-31 |
?{col}__in=a,b,c | Одно из значений | ?region__in=Москва,Санкт-Петербург |
Операторы можно комбинировать: ?start_year__gte=2020&start_year__lt=2023
По умолчанию возвращаются только базовые поля (имя, дата рождения, ИНН). Параметр subset добавляет тематический блок:
| Значение | Добавляет |
|---|---|
subset=rfm | Флаги источников, pp_person_id и все поля из реестра Росфинмониторинга |
subset=inoteka | Поля из реестра иностранных агентов: статус, основание признания, тематика, год признания/исключения, флаги прекращения работы |
Для /organisations параметра subset нет — все поля возвращаются всегда. Записи с do_not_publish возвращаются, но с обнулёнными идентификаторами и описаниями.
Рекомендуется — курсор (cursor). Сортировка на большом списке почти всегда содержит повторяющиеся значения (например, у пачки записей, обновлённых одним импортом, совпадает updated_at) — офсетная пагинация в этом случае может отдать одну и ту же строку дважды или пропустить её при переходе между страницами. Курсор кодирует позицию последней строки (значение сортировки + внутренний id-тайбрейкер) и не зависит от такого совпадения. Задайте sort в первом запросе — дальше просто передавайте next_cursor из ответа, пока он не станет null; sort/order повторно передавать не нужно, курсор уже их несёт.
# Загрузить все записи, устойчиво к дублям/пропускам import requests API = "https://api-data.ovd.info" KEY = {"X-API-Key": "<ваш_ключ>"} params = {"limit": 1000, "sort": "updated_at", "order": "desc"} rows = [] while True: r = requests.get(f"{API}/persons", headers=KEY, params=params).json() rows.extend(r["data"]) if not r["next_cursor"]: break params = {"limit": 1000, "cursor": r["next_cursor"]}
Альтернатива — offset. Проще для разовой выгрузки небольшого списка, но не гарантирует отсутствие дублей/пропусков при сортировке с повторяющимися значениями.
# Загрузить все записи постранично (offset) import requests API = "https://api-data.ovd.info" KEY = {"X-API-Key": "<ваш_ключ>"} params = {"limit": 1000, "offset": 0} rows = [] while True: r = requests.get(f"{API}/persons", headers=KEY, params=params).json() rows.extend(r["data"]) if params["offset"] + 1000 >= r["total"]: break params["offset"] += 1000
persons/organisations/profiles отдают updated_at, а pp_persecutions — last_updated; обе колонки filter, то есть поддерживают операторы __gt/__gte/__lt/__lte (см. таблицу операторов выше). Для регулярного (например, ежедневного) импорта не нужно перечитывать весь датасет — достаточно отфильтровать по отметке времени последней успешной синхронизации, отсортировать по той же колонке и пройти курсором:
# Только записи, изменённые после последней синхронизации import requests API = "https://api-data.ovd.info" KEY = {"X-API-Key": "<ваш_ключ>"} params = { "limit": 1000, "updated_at__gte": "2026-08-25T00:00:00", # отметка предыдущего запуска "sort": "updated_at", "order": "asc", } rows = [] while True: r = requests.get(f"{API}/profiles", headers=KEY, params=params).json() rows.extend(r["data"]) if not r["next_cursor"]: break params = {"limit": 1000, "cursor": r["next_cursor"]} # следующий запуск — updated_at__gte = время начала ЭТОГО запуска (не последней строки из rows)
Отметку для следующего запуска берите из времени начала текущего запуска, а не из updated_at последней полученной записи — иначе запись, изменённая в БД в момент между вашими запросами первой и последней страницы, может быть пропущена.
# Поиск по имени curl "https://api-data.ovd.info/persons?q=Иванов" \ -H "X-API-Key: <ваш_ключ>" # Персоны с полным набором полей РФМ curl "https://api-data.ovd.info/persons?subset=rfm&in_rosfinmon=true" \ -H "X-API-Key: <ваш_ключ>" # Иностранные агенты — все поля + фильтр по статусу (contains-any по всем статусам записи) curl "https://api-data.ovd.info/persons?subset=inoteka&in_inoteka=true&inoteka_statuses=Физическое лицо — иностранный агент" \ -H "X-API-Key: <ваш_ключ>" # Организации — иноагенты, не прекратившие работу, признанные с 2020 года curl "https://api-data.ovd.info/organisations?inoteka_stopped_working=false&inoteka_first_recognition_year__gte=2020" \ -H "X-API-Key: <ваш_ключ>" # Персона с историей преследований curl "https://api-data.ovd.info/persons/<uuid>?timeline=true" \ -H "X-API-Key: <ваш_ключ>" # Активные преследования curl "https://api-data.ovd.info/pp_persecutions?is_actual=true" \ -H "X-API-Key: <ваш_ключ>"
Административные страницы для работы с данными — доступны авторизованным сотрудникам.
| Страница | Описание |
|---|---|
/inoteka |
Реестр иностранных агентов. Список физических лиц и организаций с фильтрацией по типу, статусу и тексту. Карточка справа показывает основные данные, акты признания и давления, связанных участников. Форма редактирования позволяет менять все поля записи, включая статус признания, тематику деятельности и — для организаций — флаг прекращения работы. |
/politpressing |
База политических преследований. Список преследуемых с фильтрацией по типу преследования, актуальности и тексту. Карточка справа раскрывает полный профиль: фото, персональные данные, историю преследований с мерами пресечения, судебными заседаниями, приговорами и местами лишения свободы, а также оценки правозащитных организаций. |
Актуальная схема — колонки, какие из них фильтруемые и поисковые, к какому subset относятся. Ключ не нужен.
registries и timeline сюда не попадают — это не колонки profiles.parquet, а поля, которые добавляются на лету только в ответе GET /profiles/{id}?subset=full (не в списке GET /profiles и не в этой схеме). cases/evaluations — настоящие колонки (subset: full), появятся в таблице ниже.