Росстат в графиках

Официальная статистика Росстата, приведённая к графикам вместо CSV и XLSX

API roschart.ru

Статистика Росстата в JSON — тот же набор данных, по которому рисуются страницы сайта: 26 тысяч наборов, 49 миллионов значений, обновление через день.

Быстрый старт

Эти три запроса работают без ключа — их можно открыть прямо в браузере.

# что вообще есть в базе и когда обновлялось
curl 'https://roschart.ru/api/meta'

# найти наборы про инфляцию
curl 'https://roschart.ru/api/catalog?q=инфляция&limit=5'

# забрать один набор с рядами и значениями
curl 'https://roschart.ru/api/dataset/ipc-mes-06-2026-indeksy-potrebitelskih-cen-na-neprodovolstve'

Дальше — зарегистрироваться и получить ключ, затем передавать его заголовком:

curl -H 'X-API-Key: rk_…' 'https://roschart.ru/api/ids?limit=1000'

Ключ и ограничения

Ключ передаётся одним из трёх способов:

РежимЗапросов в минуту В суткиЗаписей за запрос
без ключа 20 300 100
с ключом 120 без потолка 1000

Доступ бесплатный, в том числе для коммерческих проектов. Минутный порог стоит для защиты сервера от запросов в цикле; ограничения на объём выгрузки нет.

Лимит считается на учётную запись, а не на ключ: ключи одной записи делят общую квоту. Отдельный ключ на каждое своё приложение — нормальная практика, так понятнее, что сколько расходует.

В каждом ответе приходят X-RateLimit-Tier, X-RateLimit-Limit и X-RateLimit-Remaining. При отказе — 429 и Retry-After в секундах: столько нужно подождать перед повтором.

Регистрация и личный кабинет.

Общие правила

Все ручки отвечают на GET и возвращают JSON в UTF-8 с полем ok. Методов записи в API нет.

{"ok": false, "error": "датасет не найден"}
КодЧто случилось
200всё в порядке
304ответ не изменился с прошлого раза (см. ниже про ETag)
400не хватает обязательного параметра
401ключ не найден или отключён
404нет такого набора или такого пути
429превышен лимит частоты
500сбой на нашей стороне

Кеширование

Данные меняются через день, а опрашивают их чаще. Каждый ответ несёт ETag, посчитанный от самого тела. Пришлите его обратно в If-None-Match — и получите 304 в несколько байт вместо мегабайта JSON:

curl -H 'If-None-Match: "a1b2c3…"' 'https://roschart.ru/api/meta'

Ещё дешевле: запомнить upload_id из /api/meta и вообще ничего не перезакачивать, пока он тот же. Это одна строка на всю выгрузку — если она не изменилась, не изменилось ни одно значение в базе.

Страницы

Где есть список, там работают limit и offset, а в ответе приходят total (сколько всего подходит), count (сколько отдано) и offset. limit молча урезается до потолка вашего уровня — проверяйте count, а не надейтесь, что попросили тысячу и получили тысячу.

Кросс-доменные запросы

Разрешены отовсюду: Access-Control-Allow-Origin: *, так что запрос можно делать прямо из браузера. Учтите, что ключ в коде страницы виден всем — расходовать вашу квоту сможет любой.

Идентификаторы

Идентификатор набора — читаемая строка латиницей вроде ipc-mes-06-2026-indeksy-potrebitelskih-cen-na-neprodovolstve. Он же стоит в адресе страницы сайта: /dataset/<id>. Идентификаторы устойчивы, но не вечны: при исправлении названия набора адрес меняется, и старый начинает переадресовывать на новый. Если храните id у себя — сверяйтесь с /api/changes.

Что такое набор данных

Набор — один лист из книги Росстата, приведённый к общему виду. Это не показатель: если Росстат опубликовал промышленное производство тремя таблицами, будет три набора.

Внутри набора всё держится на двух параллельных массивах:

Два вида наборов различаются полем kind:

У ряда, кроме label, бывают row и col: в исходной таблице шапка нередко двухэтажная («мужчины / городское население»), и мы сохраняем обе части отдельно, а label — то, что показывается человеку.

Единица измерения (unit) бывает null: у Росстата она нередко написана в заголовке таблицы, отдельного поля в книге нет. Тогда смотрите title и footnotes.

Поле title — вычищенное название, пригодное для показа; title_raw — ровно то, что напечатано в книге, вместе с номерами сносок и годами в скобках. Для ссылки на источник берите title_raw и source_url.

Ручки

GET /api/meta — состояние базы

Весит меньше килобайта. С него удобно начинать синхронизацию: если upload_id не изменился, остальное можно не перезапрашивать.

{
  "ok": true, "ready": true,
  "upload_id": "90ae18251ef86537",
  "generated_at": "2026-08-11T18:23:48+00:00",
  "committed_at": "2026-08-11T19:02:51+00:00",
  "source": "https://rosstat.gov.ru/",
  "n_datasets": 26461,
  "n_values": 49100146,
  "breakdown": [{"kind": "crosssection", "freq": "none", "c": 18141, "v": 44485654}, …]
}

generated_at — когда парсер разобрал книги, committed_at — когда выгрузка была принята сайтом. ready: false означает, что приём выгрузки идёт прямо сейчас: данные в этот момент отдаются прежние, целые.

GET /api/sections — разделы

Рубрики Росстата с числом наборов и значений в каждой. Названия разделов, отличающиеся только годом выпуска сборника, склеены в одно: год издания внутри названия ничего не значит.

{"ok": true, "sections": [
  {"section": "Промышленное производство", "c": 2694, "v": 6329150}, …]}

GET /api/catalog — поиск наборов

ПараметрЗначение
qпоисковая строка по названию; можно по-русски, регистр не важен
kindtimeseries или crosssection
freqannual, quarterly, monthly
sectionраздел ровно так, как он пришёл в /api/sections
flat1 — не схлопывать выпуски одного показателя в одну строку
groupключ группы из group_key: все выпуски одного показателя
limit, offsetстраница; по умолчанию 60

Росстат публикует одну и ту же таблицу каждый месяц новой книгой, и без группировки поиск по слову «инфляция» возвращал бы сорок почти одинаковых строк. По умолчанию такие выпуски свёрнуты в один самый свежий набор с полем n_editions; развернуть группу — group= с её group_key, отключить схлопывание совсем — flat=1.

{"ok": true, "total": 437, "count": 2, "offset": 0, "items": [
  {"ds_id": "ipc-mes-06-2026-…", "title": "Индексы потребительских цен…",
   "unit": null, "freq": "monthly", "kind": "timeseries",
   "section": "Цены, инфляция", "n_series": 2, "n_periods": 432, "n_values": 462,
   "period_first": "1991-01", "period_last": "2026-12",
   "content_hash": "489e37d1b955a6e4", "group_key": "f9aa1ee825d27982",
   "n_editions": 1, "source_url": "https://rosstat.gov.ru/storage/…xlsx"}, …]}

content_hash считается от значений набора. Совпал — содержимое ровно то же, что вы уже скачали, можно не забирать.

GET /api/ids — все идентификаторы

Компактный список: id, название, вид, частота. Нужен, чтобы завести у себя зеркало каталога, не выкачивая наборы целиком.

Параметры: limit, offset и updated_since — дата в виде 2026-08-01, после которой набор менялся. С ней обход становится добавочным: раз в пару дней спрашиваете, что изменилось со дня прошлой сверки, и перекачиваете только это.

GET /api/dataset/{id} — набор целиком

ПараметрЗначение
max_seriesсколько рядов вернуть; у региональных наборов их бывает под две тысячи
qотобрать ряды по подстроке в подписи — например, только «Москва»
limit, offsetстраница по рядам
format=csvотдать таблицей, а не JSON
{"ok": true, "dataset": {
  "id": "…", "title": "…", "unit": null, "freq": "monthly", "kind": "timeseries",
  "section": "Цены, инфляция", "source_url": "https://rosstat.gov.ru/…",
  "periods": ["1991-01", "1991-02", …],
  "series": [{"label": "к концу предыдущего месяца", "row": "к концу предыдущего месяца",
              "col": null, "values": [109.0, 105.9, 104.6, …]}],
  "series_total": 2, "series_shown": 1,
  "n_series": 2, "n_periods": 432, "n_values": 462,
  "footnotes": […], "related": […], "intro": "…", "tags": […],
  "title_raw": "…", "description": "…"}}

Если series_shown меньше series_total, вы получили не весь набор. related — соседние наборы того же показателя, footnotes — сноски из книги; в них у Росстата оговорки вроде «без учёта Крыма».

CSV удобен для выгрузки в таблицу и отдаётся с заголовком Content-Disposition, то есть скачивается файлом:

curl -o ipc.csv 'https://roschart.ru/api/dataset/ipc-mes-06-2026-…?format=csv'

GET /api/series/{id}/{i} — один ряд

Ряд под номером i: нумерация с нуля, порядок тот же, что в наборе. Пригодится, когда нужна одна линия, а не набор целиком.

GET /api/chart/{id} — готовый график

Отдаёт то же, что нарисовано на странице сайта: вид графика, отобранные ряды, подписи оси, цвета, примечание. Избавляет от необходимости самому решать, чем рисовать набор — линией, столбиками или тепловой картой на две тысячи регионов.

Параметры: q — отбор рядов, theme=dark — цвета для тёмного оформления. В ответе, кроме periods и series, приходят chart_kind, y_axis, row_label и note.

GET /api/revisions/{id} — правки задним числом

Росстат переписывает уже опубликованные цифры: уточнил методику — и прошлогоднее значение стало другим. Мы храним прежние значения и отдаём, что именно изменилось: период, было, стало, когда заметили. В первоисточнике старое значение не сохраняется.

GET /api/changes — журнал изменений

Что произошло между выгрузками: наборы добавились, изменились, пропали. Параметры: kind (added | changed | removed), id — история одного набора, limit, offset.

{"ok": true, "total": 1123,
 "batches": [{"changed_at": "2026-08-10T08:11:13+00:00", "added": 140, "changed": 2, "removed": 1}, …],
 "items": [{"changed_at": "…", "ds_id": "…", "kind": "removed", "title": "…",
            "old_values": 96, "new_values": 0, "old_last": "2017"}, …]}

То же есть лентой: /changes/rss.xml.

GET /api/suggest — подсказки поиска

По началу слова возвращает уточнения и подходящие наборы — то же, что выпадает под строкой поиска на сайте. Для полноценного поиска — /api/catalog.

Рецепты

Забрать весь каталог

26 тысяч наборов — это 27 запросов с ключом по 1000 записей. Уложится минуты в три.

off=0
while :; do
  n=$(curl -s -H "X-API-Key: $KEY" \
        "https://roschart.ru/api/ids?limit=1000&offset=$off" \
      | tee -a ids.jsonl | grep -o '"count":[0-9]*' | cut -d: -f2)
  [ "$n" -lt 1000 ] && break
  off=$((off + 1000))
done

Держать свою копию в актуальном состоянии

  1. раз в сутки спросить /api/meta;
  2. если upload_id прежний — на этом закончить;
  3. если новый — взять /api/changes и обновить только перечисленные там наборы;
  4. сверить content_hash перед закачкой: он меняется только вместе со значениями.

Полный обход при каждой выгрузке тоже возможен, но избыточен: за выгрузку меняется несколько сотен наборов из двадцати шести тысяч.

Показать график у себя, не рисуя его

Для этого API не нужен: /embed/<id> — страница с одним графиком для вставки в iframe, /og/<id>.png — картинка 1200×630 для соцсетей.

Чего в данных нет

Ограничения, о которых лучше знать заранее:

Данные Росстата открытые и доступны для свободного использования, в том числе коммерческого. Требования первоисточника — сохранять ссылку на источник и не искажать цифры — переходят и на тех, кто берёт данные у нас. Подробно на странице условий использования.

Ссылка на roschart.ru приветствуется: по ней читатель дойдёт до исходной таблицы и сносок к ней.

Машинное описание тех же ручек — /openapi.json (OpenAPI 3.0.3), по нему генерируются клиенты для Swift, Kotlin, Dart и других языков.

Состав каталога опубликован отдельным снимком с постоянным идентификатором: doi.org/10.5281/zenodo.22107658 — метаданные всех наборов таблицей, со ссылками на выгрузку каждого.

Нужен лимит выше или нестандартная выгрузка — напишите нам.