llm-analytics-mcp
Аналитическая система на базе LLM с интеграцией MCP
MCP-сервер, который даёт языковой модели набор инструментов для анализа табличных данных: загрузка, очистка, построение графиков, сборка отчёта. Собственный чат-интерфейс не разрабатывается — используется веб-интерфейс готовой платформы (Claude как основной клиент, ChatGPT как альтернативный).
Один и тот же реестр инструментов публикуется по двум протоколам сразу:
Протокол | Эндпоинт | Клиент |
MCP (Streamable HTTP) |
| Claude — веб, десктоп, любой MCP-клиент |
REST + OpenAPI |
| ChatGPT Custom GPT Action |
Что умеет система
12 инструментов, 5 скиллов. Полный список — вызовом describe_system
или в ARCHITECTURE.md.
Инструмент | Скилл | Назначение |
| — | Каталог доступных данных |
| DataLoadingSkill | Загрузка CSV/TSV/Excel/JSON/Parquet из каталога, пути или URL |
| DataLoadingSkill | Структура, типы, пропуски, дубликаты |
| DataCleaningSkill | Дубликаты, пропуски, нормализация, выбросы |
| InsightGenerationSkill | Автоподбор плана анализа под структуру данных |
| VisualizationSkill | Динамика метрики во времени |
| VisualizationSkill | Гистограмма или бар-чарт (тип выбирается сам) |
| VisualizationSkill | Тепловая карта корреляций |
| VisualizationSkill | Разрез метрики по категориям |
| InsightGenerationSkill | Проверяемые числа для текста отчёта |
| ReportingSkill | Отчёт в Markdown, HTML и PDF |
| — | Интроспекция: состав скиллов и инструментов |
Дополнительные возможности:
Автоподбор анализа —
suggest_analysisопределяет, какая колонка является временной осью, какие метриками, какие разрезами, и возвращает готовый план вызовов с обоснованием каждого шага.Мульти-формат и мульти-источник — CSV, TSV, Excel, JSON, Parquet; каталог, локальный путь или HTTP(S)-ссылка. Последнее принципиально для веб-сценария: файл, загруженный в браузерный чат, серверу недоступен.
Сборка отчёта одной командой —
build_reportсам достраивает недостающие графики и выдаёт документ в трёх форматах.
Related MCP server: Claude Data Buddy
Установка
Требуется Python 3.10 и новее.
git clone <адрес-репозитория>
cd llm-analytics-mcp
python -m venv .venv
source .venv/bin/activate # Windows: .venv\Scripts\activate
pip install -r requirements.txtШаг 1. Тестовые данные
Данные в репозитории сгенерированы синтетически по схеме Superstore. ТЗ прямо это допускает: «вы можете сгенерировать данные самостоятельно или взять известный датасет».
python scripts/prepare_dataset.py --synthetic --rows 4000Готовые файлы уже лежат в data/ — команда нужна, только если вы хотите
пересоздать их или изменить объём.
Почему синтетика, а не Kaggle
Генератор даёт контроль над тем, что именно демонстрирует система:
Заложены проверяемые закономерности — восходящий тренд, годовая сезонность с пиком в конце года и связь «скидка выше 30% → отрицательная прибыль». Благодаря этому выводы анализа содержательны, а не случайны.
Дефекты внесены намеренно. Реальный Superstore практически идеально чист: без пропусков и дубликатов
DataCleaningSkillотчитался бы «удалено 0 строк», и продемонстрировать очистку было бы нечем.Воспроизводимость. Фиксированный
seed=42— проверяющий получает ровно те же данные и те же числа в отчёте, что и в примере.Репозиторий самодостаточен. Не нужен аккаунт Kaggle, чтобы запустить проект.
Загрузка реального Superstore тоже поддерживается — структура колонок совпадает:
python scripts/prepare_dataset.py --input ~/Downloads/Sample-Superstore.csvЧто создаёт скрипт
Файл | Назначение |
| Данные, приведённые к колонкам из ТЗ |
| Та же таблица с внесёнными дефектами |
Колонки: Date, Product, Region, Sales, Quantity, Profit (из ТЗ)
плюс разрезы Category, Sub-Category, Segment, Discount, Ship Mode.
Период — 2021–2024, 48 месяцев.
Состав дефектов печатается при запуске и детерминирован:
Дефект | Объём |
Пропуски в | ~3.5% / 4.5% / 2% |
Полные дубликаты строк | ~0.8% |
Разнобой в написании | ~6% строк |
Экстремальные выбросы в | 12 строк |
Альтернативный формат даты ( | ~10% строк |
Шаг 2. Проверка без сервера
Сквозной прогон всей цепочки — от загрузки до PDF-отчёта:
PYTHONPATH=src python -m analytics_mcp.selfcheckСкрипт повторяет то, что делает LLM в диалоге, но детерминированно. Полезен как smoke-тест перед демонстрацией: если он проходит, проблема почти наверняка в интеграции, а не в аналитике.
Шаг 3. Запуск сервера
PYTHONPATH=src uvicorn analytics_mcp.app:app --host 127.0.0.1 --port 8000Проверка:
curl http://127.0.0.1:8000/healthПолезные адреса:
Адрес | Что это |
| Статус и число зарегистрированных компонентов |
| Swagger UI: все инструменты можно вызвать руками |
| Спецификация для Custom GPT Action |
| MCP-эндпоинт |
Если порт занят. Стартовавший ранее процесс может продолжать отвечать старым кодом — симптом обманчивый:
/healthотвечает, а изменения не применяются. Перед перезапуском:pkill -f uvicorn.
Шаг 4. Публичный адрес через ngrok
Claude обращается к серверу снаружи, поэтому нужен HTTPS-адрес.
# 1. Установка и регистрация: https://ngrok.com/download
ngrok config add-authtoken <ваш-токен>
# 2. В личном кабинете ngrok зарезервируйте бесплатный статический домен
# (Domains -> Create Domain). Без него адрес меняется при каждом
# перезапуске, и настройку коннектора придётся повторять.
# 3. Запуск туннеля
ngrok http 8000 --domain=ваш-домен.ngrok-free.appЗатем пропишите адрес в окружении и перезапустите сервер:
cp .env.example .env
# в .env укажите:
# PUBLIC_BASE_URL=https://ваш-домен.ngrok-free.app
export PUBLIC_BASE_URL=https://ваш-домен.ngrok-free.app
export MCP_ALLOWED_HOSTS='127.0.0.1:*,localhost:*,*.ngrok-free.app'
PYTHONPATH=src uvicorn analytics_mcp.app:app --host 127.0.0.1 --port 8000Самая частая причина «не подключается». MCP SDK по умолчанию включает защиту от DNS rebinding и принимает только заголовок
Hostвидаlocalhost. За туннелемHostсодержит домен ngrok, и запрос отклоняется на этапе подключения коннектора, без внятной ошибки в интерфейсе. ПеременнаяMCP_ALLOWED_HOSTSрешает ровно эту проблему.
Шаг 5. Подключение к Claude (основной сценарий)
Откройте Settings → Connectors → Add custom connector.
Укажите адрес:
https://ваш-домен.ngrok-free.app/mcp(обратите внимание на суффикс/mcp).Сохраните и убедитесь, что коннектор перешёл в состояние подключённого.
В новом диалоге включите коннектор
analytics_mcpчерез меню инструментов.Скопируйте содержимое
prompts/system_prompt.mdв описание проекта (Project instructions) — это задаёт порядок вызовов.
Проверочный запрос: «Какие датасеты доступны?» — модель должна вызвать
list_datasets и показать содержимое каталога.
Шаг 6. Подключение к ChatGPT (альтернативный сценарий)
Выгрузите спецификацию с публичным адресом:
PUBLIC_BASE_URL=https://ваш-домен.ngrok-free.app \ PYTHONPATH=src python scripts/export_openapi.pyСоздайте Custom GPT: Explore GPTs → Create → Configure.
Create new action → Schema — вставьте содержимое
openapi.json.Authentication: None.
В поле Instructions вставьте
prompts/system_prompt.md.
Подробности и особенности отображения графиков —
в prompts/gpt_action_setup.md.
Демонстрационный сценарий
Порядок запросов подобран так, чтобы на скриншотах была видна цепочка вызовов, а не один запрос. Ключевой кадр — шаг 4: видно, что планирует модель, а не хардкод.
# | Запрос пользователю | Ожидаемые вызовы |
1 | Какие датасеты доступны? |
|
2 | Загрузи superstore_raw и опиши структуру |
|
3 | Почисти данные |
|
4 | Что здесь стоит проанализировать? |
|
5 | Построй эти графики |
|
6 | Сделай отчёт с выводами и рекомендациями |
|
Пример результата — docs/report_example.md,
графики — в docs/plots/.
Скриншоты работы
Материалы демонстрации лежат в docs/screenshots/:
Файл | Что показано |
Claude вызывает | |
Отчёт | |
Сравнение версий датасета «с заполнением пропусков» и «без» | |
Модель проверяет гипотезы из отчёта новыми вызовами инструментов | |
Приоритизированный список направлений дальнейшего анализа | |
Построение графиков; модель явно отмечает, чего инструменты не умеют |
Скриншоты показывают ключевое свойство системы: цепочкой вызовов управляет LLM. Модель сама решает, какие инструменты вызвать, находит ограничения набора (например, отсутствие фильтрации строк) и сообщает о них вместо того, чтобы подгонять вывод.
Проверка интеграции
# Полный цикл по обоим транспортам: initialize, tools/list, tools/call,
# возврат изображения, обработка ошибочных аргументов
python scripts/integration_test.pyСтруктура репозитория
llm-analytics-mcp/
├── README.md инструкция (этот файл)
├── ARCHITECTURE.md архитектура и роль MCP/скиллов
├── openapi.json спецификация для Custom GPT Action
├── requirements.txt
├── .env.example
├── data/ тестовые данные
├── docs/
│ ├── report_example.md/html/pdf пример сгенерированного отчёта
│ ├── plots/ примеры графиков
│ └── screenshots/ скриншоты диалога
├── prompts/
│ ├── system_prompt.md инструкция для LLM
│ └── gpt_action_setup.md настройка Custom GPT Action
├── scripts/
│ ├── prepare_dataset.py подготовка данных
│ ├── export_openapi.py выгрузка спецификации
│ └── integration_test.py проверка обоих транспортов
└── src/analytics_mcp/
├── core/ реестр инструментов, хранилище, модели
├── skills/ бизнес-логика этапов анализа
├── tools/ инструменты, публикуемые наружу
├── transports/ адаптеры MCP и REST
├── rendering/ оформление графиков, артефакты
├── app.py сборка ASGI-приложения
└── selfcheck.py сквозная самопроверкаКак добавить свой инструмент
Ядро при этом не меняется. Создайте файл src/analytics_mcp/tools/my_tools.py:
from __future__ import annotations
from analytics_mcp.core.datasets import store
from analytics_mcp.core.registry import tool
@tool(tags=("stats",), skill="DataLoadingSkill", title="Топ значений")
def top_values(column: str, dataset_id: str | None = None, limit: int = 10) -> dict:
"""Возвращает самые частые значения колонки.
Args:
column: Имя колонки.
dataset_id: Датасет. По умолчанию — последний использованный.
limit: Сколько значений вернуть.
"""
record = store.get(dataset_id)
record.require_column(column)
counts = record.df[column].value_counts().head(limit)
return {str(k): int(v) for k, v in counts.items()}Перезапустите сервер. Инструмент появится сразу в обоих протоколах:
в tools/list у MCP и в /openapi.json у REST. Пакет tools импортирует
свои модули автоматически, JSON-схема выводится из сигнатуры, описание —
из докстринга.
Известные ограничения
Названы сознательно — это границы прототипа, а не недоделки:
Хранилище датасетов в памяти. При перезапуске сервера загруженные данные теряются. Для прототипа приемлемо; в продакшене — Redis или диск.
Нет авторизации. Демонстрационный стенд за временным туннелем. Для продакшена — API-ключ в заголовке и проверка на стороне FastAPI.
Нет фильтрации строк. Инструменты работают с датасетом целиком: срез «только регион West за 2024 год» построить нельзя. Это заметно в демонстрации — модель честно сообщает, чего не может посчитать, вместо подгонки вывода.
Пять скиллов, а не больше. Сознательный выбор: лучше пять работающих, чем десять формальных.
Юнит-тестов нет — только сквозная самопроверка
selfcheck.pyи интеграционный тест обоих транспортов.
This server cannot be deployed
Maintenance
Related MCP Connectors
Clean messy tabular data and render publication-ready PNG charts from your AI assistant.
- OleanderOAuthdev.oleander
The all-in-one data stack for agents. Upload files, run SQL, evolve tables, and render charts.
Explore, clean, transform and export your Mammoth Analytics data from an AI client.
Ask questions about a CSV in plain English and get answers, charts and cleaned data back.
Related MCP Servers
- FlicenseNot gradedqualityDmaintenanceEnables AI-powered business intelligence and data analysis using pandas and LLM code generation. Supports automated data processing, statistical analysis, and visualization creation through natural language interactions.15-
- FlicenseNot gradedqualityDmaintenanceEnables conversational analysis of CSV and Parquet files through natural language, providing statistics, summaries, data type information, and comprehensive multi-step data analysis.-
- AlicenseNot gradedqualityCmaintenanceGives LLM agents access to local and remote data via databases, files, graphs, and structured documents, along with a full data science toolkit for analysis and modeling.34 PyPI11Apache 2.0
- AlicenseBqualityBmaintenanceEnables LLMs to work with Excel and CSV files through structured tools for workbook operations, formatting, charts, ETL, analysis, and more.695MIT