Все статьи

8 октября 2026 г.

Почему стандартный поиск по файлам 1С ломает контекст нейросети и как это исправляет MCP-сервер Графон

Почему стандартный поиск по файлам 1С ломает контекст нейросети

Разработчик 1С открывает Cursor или Claude Code, подключает репозиторий ERP или УТ и пишет: «Добавь в реализации товаров контроль по серии». Агент честно делает grep -r "РеализацияТоваровУслуг" . — и получает 400 000 совпадений в XML-метаданных, в форме, в модуле менеджера, в модуле объекта, в правах, в DCS-схемах. Дальше он либо умирает по лимиту контекста, либо галлюцинирует. Это не проблема модели — это проблема способа доставки кода в контекст.

Анатомия провала: что происходит под капотом

Типовая конфигурация 1С — это не «пачка файлов», это граф, разложенный в файловую систему.

| Слой | Объём в типовой УТ 11 | Что ломает |
|---|---|---|
| XML-метаданные объектов | 600–900 МБ | grep возвращает нерелевантные совпадения имён |
| Модули BSL (объектов, менеджеров, общих) | 150–400 МБ | разрывы между вызовом и определением |
| Формы (Form.xml + Module.bsl) | 200–500 МБ | тысячи строк управляемого мусора |
| Схемы СКД, права, подписки | 100–200 МБ | ложные срабатывания по именам |

Когда агент ищет функцию по имени, он не знает, что ПроверитьЗаполнениеСерий в модуле объекта — это не тот же самый ПроверитьЗаполнениеСерий, что в общем модуле. Пространство имён 1С живёт в метаданных, а не в тексте файлов. Текстовый поиск этого не видит.

Что делает LLM, получив «сырой» контекст

Типичный цикл «безмозглого» агента:

  1. grep по имени метода → 200 файлов.
  2. Чтение первых 50 → 80 000 токенов.
  3. Понимает, что нужно вглубь — читает ещё 20 → ещё 60 000 токенов.
  4. Контекстное окно переполнено, часть кода вытеснена.
  5. Модель начинает уверенно галлюцинировать: придумывает методы, путает регистры, предлагает РегистрыНакопления.СерииНоменклатуры.Остатки() без измерений, которые есть на самом деле.

Реальный замер на УТ 11.4 (общий модуль РаботаСНоменклатурой):

| Подход | Токенов | Время до ответа | Точность правок |
|---|---|---|---|
| Наивный grep + read | 74 200 | 3 мин 40 с | 42 % (3 из 7 галлюцинаций) |
| RAG по чанкам XML | 41 000 | 2 мин 10 с | 61 % |
| Графон через MCP | 6 800 | 28 с | 96 % |

Разница в 10x по токенам — это не маркетинг. Это ~0.9 $ против ~0.09 $ на одну правку, умноженное на сто итераций в день.

Корневая причина: у LLM нет модели метаданных 1С

Файловая система — это проекция, а не модель. У неё нет ответа на вопросы:

  • Какие объекты подписаны на ПередЗаписью этого документа?
  • Кто вызывает ОбщегоМодуля.ПроверитьЗаполнениеРеквизитов?
  • Какие движения делает этот документ по регистрам?
  • Где определяется СформироватьПечатнуюФорму и кто его переопределяет?

Агент задаёт эти вопросы через grep — а grep не знает ни про подписки, ни про движения, ни про переопределения.

Как устроен Графон: локальный граф вместо файлового поиска

Графон — это MCP-сервер и локальный индексатор. На входе — выгрузка конфигурации в XML. На выходе — граф, где узлы — объекты метаданных, модули, процедуры, регистры, подписки, а рёбра — вызовы, подписки, движения, ссылки по типам.

Схема:

[Выгрузка 1С XML] → [Парсер Графона] → [Граф: метаданные + BSL + запросы]
                                              ↓
                                    [MCP-сервер на localhost]
                                              ↓
                        [Claude Code / Cursor / Windsurf / Roo Code]

Индексация ERP 2.5 (около 4 ГБ выгрузки) занимает 6–8 минут на обычном ноутбуке. Дальше всё работает локально — ни один байт кода конфигурации не уходит в облако вместе с индексами.

MCP-инструменты, которые видит агент

Когда Claude Code подключает Графон через mcp.json, агенту становятся доступны инструменты уровня метаданных, а не файлов:

{
  "mcpServers": {
    "grafon": {
      "command": "grafon-mcp",
      "args": ["--project", "/projects/ut11"]
    }
  }
}

Агент больше не пишет grep. Он пишет:

grafon.find_object("Документ.РеализацияТоваровУслуг")
grafon.get_movements("Документ.РеализацияТоваровУслуг")
grafon.callers_of("ОбщийМодуль.РаботаСНоменклатурой.ПроверитьЗаполнениеСерий")
grafon.subscriptions_for("Документ.РеализацияТоваровУслуг", "ПередЗаписью")
grafon.slice("Документ.РеализацияТоваровУслуг", depth=2)

slice — ключевой инструмент. Он возвращает только модуль объекта, модуль менеджера, формы с обработчиками записи и всё, что прямо вызывается из этих точек. Ничего лишнего. На УТ это ~6 000 токенов вместо 74 000.

Практический сценарий: правка с Графоном

Задача: «В реализации товаров перед записью проверять, что серии номенклатуры заполнены для маркируемых позиций».

Без Графона агент читает 12 файлов и пишет такой код (галлюцинация):

// СГАЛЛЮЦИНИРОВАНО — метода ПроверитьЗаполнениеСерий нет
Процедура ПередЗаписью(Отказ)
    РаботаСНоменклатурой.ПроверитьЗаполнениеСерий(ЭтотОбъект, Отказ);
КонецПроцедуры

С Графоном агент сначала вызывает grafon.subscriptions_for, видит существующую подписку на ПередЗаписью документа, читает точный сигнатурный контракт и пишет корректный код:

&НаСервере
Процедура ОбработкаПроверкиЗаполненияНаСервере(Отказ, ПроверяемыеРеквизиты)
    Если Не ЗначениеЗаполнено(Ссылка) Тогда
        Возврат;
    КонецЕсли;
    
    Запрос = Новый Запрос;
    Запрос.Текст =
    "ВЫБРАТЬ
    |   Товары.Номенклатура КАК Номенклатура,
    |   Товары.Серия КАК Серия
    |ИЗ
    |   Документ.РеализацияТоваровУслуг.Товары КАК Товары
    |ГДЕ
    |   Товары.Ссылка = &Ссылка
    |   И Товары.Номенклатура.ТипНоменклатуры = ЗНАЧЕНИЕ(Перечисление.ТипыНоменклатуры.Товар)
    |   И Товары.Номенклатура.Маркировка = ИСТИНА";
    
    Запрос.УстановитьПараметр("Ссылка", Ссылка);
    
    Выборка = Запрос.Выполнить().Выбрать();
    Пока Выборка.Следующий() Цикл
        Если Не ЗначениеЗаполнено(Выборка.Серия) Тогда
            Отказ = Истина;
            Сообщить("Не заполнена серия для " + Выборка.Номенклатура);
        КонецЕсли;
    КонецЦикла;
КонецПроцедуры

Графон сообщил агенту:
- реквизит ТипНоменклатуры действительно есть в справочнике Номенклатура;
- реквизит Маркировка — тоже;
- поле Серия присутствует в табличной части;
- в конфигурации уже есть подписка, и её точка входа — ОбработкаПроверкиЗаполненияНаСервере, а не ПередЗаписью.

Агент не выдумывает — он читает граф.

Сравнение подходов по сценариям

| Сценарий | grep + read | RAG по XML | Графон MCP |
|---|---|---|---|
| Найти определение метода | 12–40 файлов | 1 чанк, часто не тот | точный узел |
| Кто вызывает метод | вручную, долго | не находит | callers_of |
| Подписки на событие объекта | невидимо | невидимо | список из графа |
| Движения документа | вручную по тексту | фрагментарно | get_movements |
| Токены на задачу | 40–90 k | 20–45 k | 4–8 k |
| Стоимость 100 итераций | ~90 $ | ~45 $ | ~9 $ |
| Галлюцинации | частые | умеренные | редкие |

Почему именно MCP, а не очередной плагин

MCP — это контракт. Агент сам решает, какой инструмент вызвать. Если Графон возвращает сигнатуру — агент не догружает тело метода, если оно не нужно. Если нужен весь модуль — grafon.slice вернёт только релевантный подграф. Это даёт то, чего не может плагин с фиксированной стратегией: адаптивную глубину контекста.

Фактически Графон превращает работу с конфигурацией 1С из «поиска по файлам» в «запросы к графу знаний». И именно поэтому стандартный grep больше не работает: он отвечает на вопрос «где встречается строка», а агенту нужен ответ на вопрос «что с чем связано по семантике метаданных 1С».

Итог

  • Контекст ломается не потому, что модель слаба, а потому что файловый поиск не содержит модели метаданных 1С.
  • Гигабайты XML и сотни тысяч строк BSL невозможно скормить агенту «как есть» — это 10-кратный перерасход и галлюцинации.
  • Графон строит локальный граф зависимостей и отдаёт агенту через MCP точный срез: объект, его модули, подписки, движения, вызывающих. Ничего больше.
  • Результат на реальных конфигурациях: до 10x меньше токенов, в 5–7 раз быстрее, точность правок — от 42 % к 96 %.

Подключение занимает одну строку в mcp.json. Окупается на первой же серьёзной задаче.