Все статьи

11 сентября 2026 г.

AST-парсер BSL для передачи метаданных в LLM: архитектура, MCP и экономия токенов

Почему конфигурация 1С убивает контекстное окно LLM

Типовая ERP или УТ — это 60–120 тысяч объектов метаданных и сотни тысяч строк BSL. Выгрузка в XML весит гигабайты, один общий модуль вроде ОбщегоНазначения содержит десятки тысяч строк, а модуль формы документа — ещё несколько тысяч. Когда разработчик открывает Cursor или Claude Code и просит «добавь проверку в проведении реализации», агент делает то, что умеет: читает файлы. Много файлов.

Результат предсказуем:

  • контекстное окно переполняется на 30–40% задачи;
  • агент теряет середину промпта и «забывает» ограничения;
  • начинаются галлюцинации: вызовы несуществующих методов, путаница между ОбработкаПроведения и ОбработкаЗаполнения;
  • стоимость токенов растёт в 5–10 раз без роста качества.

Причина не в модели. Причина в том, что агенту скармливают файлы, а не семантику кода.

Что даёт AST-парсинг BSL

AST (Abstract Syntax Tree) — это разбор модуля BSL на структуру: процедуры, функции, переменные, вызовы, условия, циклы, обращения к метаданным. В отличие от регулярных выражений, AST корректно понимает вложенность, экспортные директивы, директивы компиляции &НаКлиенте, &НаСервереБезКонтекста, области #Область.

Из AST строится три ключевых артефакта:

  1. Таблица символов — каждая процедура и функция с точной сигнатурой, расположением и признаком экспорта.
  2. Граф вызовов — кто кого вызывает, включая неявные вызовы через Выполнить() и подписки на события.
  3. Связь кода с метаданными — какие объекты, реквизиты, регистры и формы затрагивает метод.

Именно эти три слоя превращают «простыню XML» в навигируемую карту.

Архитектура: от XML-выгрузки до MCP-сервера

Выгрузка конфигурации (XML/EDT)
        │
        ▼
┌───────────────────────┐
│  Парсер метаданных    │  ← объекты, реквизиты, формы, подписки
└───────────────────────┘
        │
        ▼
┌───────────────────────┐
│  AST-парсер BSL       │  ← процедуры, вызовы, области, директивы
└───────────────────────┘
        │
        ▼
┌───────────────────────┐
│  Локальный граф       │  ← nodes: методы/объекты, edges: вызовы/ссылки
└───────────────────────┘
        │
        ▼
┌───────────────────────┐
│  MCP-сервер Графон    │  ← tools: search, slice, call_graph, metadata
└───────────────────────┘
        │
        ▼
Claude Code / Cursor / Windsurf

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

Как выглядит срез вместо простыни

Без AST-слоя агент читает модуль документа целиком:

// Модуль объекта: Документ.РеализацияТоваровУслуг
// ... 4200 строк, из них нужны 12
Процедура ОбработкаПроведения(Отказ, РежимПроведения)
    // 180 строк логики, вызовы 14 общих модулей
КонецПроцедуры

С Графоном агент сначала спрашивает граф:

{
  "method": "tools/call",
  "params": {
    "name": "grafon_bsl_slice",
    "arguments": {
      "symbol": "Документ.РеализацияТоваровУслуг.ОбработкаПроведения",
      "depth": 2,
      "include": ["signature", "callees", "metadata_refs"]
    }
  }
}

И получает компактный срез:

{
  "symbol": "Документ.РеализацияТоваровУслуг.ОбработкаПроведения",
  "signature": "ОбработкаПроведения(Отказ, РежимПроведения)",
  "file": "Documents/РеализацияТоваровУслуг/Ext/ObjectModule.bsl",
  "lines": [1240, 1420],
  "metadata_refs": [
    "РегистрНакопления.ТоварыОрганизаций",
    "РегистрНакопления.СебестоимостьТоваров",
    "Справочник.Номенклатура"
  ],
  "callees": [
    "ОбщегоНазначения.СообщитьПользователю",
    "ПроведениеДокументов.ПровестиДвижения",
    "БухгалтерскийУчет.ОтразитьРеализацию"
  ]
}

Только после этого агент запрашивает тела 3–4 действительно нужных процедур. Вместо 4200 строк — 150.

Практический пример: добавляем контроль остатков

Задача: «Не проводить реализацию, если товара не хватает на складе». Агент через MCP находит точку расширения:

&НаСервере
Процедура ОбработкаПроверкиЗаполнения(Отказ, ПроверяемыеРеквизиты)

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

Выборка = Запрос.Выполнить().Выбрать();
Пока Выборка.Следующий() Цикл
Остатки = ОстаткиПоРегистру(Выборка.Номенклатура, Ссылка.Склад);
Если Остатки < Выборка.Количество Тогда
Отказ = Истина;
СообщитьПользователю(
НСтр("ru = 'Недостаточно товара на складе: '")
+ Выборка.Номенклатура);
КонецЕсли;
КонецЦикла;

КонецПроцедуры

Графон подсказал агенту, что ОстаткиПоРегистру уже существует в общем модуле УправлениеЗапасами, и не дал сгенерировать дубль. Это и есть главный эффект: агент не изобретает методы, а переиспользует существующие сигнатуры.

Сравнение: с Графоном и без

| Метрика | Без AST/MCP | С Графоном | Выигрыш |
|---|---|---|---|
| Прочитано строк кода на задачу | 8 000–15 000 | 600–1 500 | ~10× |
| Токенов в промпте | 120 000+ | 12 000 | ~10× |
| Стоимость одной задачи (Sonnet) | ~$1.8 | ~$0.18 | ~10× |
| Время до первого ответа | 45–90 с | 8–15 с | 5× |
| Галлюцинированные методы | 3–7 на задачу | 0–1 | ↓ 90% |
| Точность попадания в файл | ~55% | ~95% | +40 п.п. |

Замеры на конфигурации ~90 000 объектов метаданных, индекс Графона ~1.2 ГБ, время холодной сборки — 4–6 минут.

MCP-инструменты, которые реально нужны агенту

  • grafon_search_metadata — поиск объекта по имени, синониму, реквизиту.
  • grafon_bsl_slice — срез процедуры с сигнатурой и ссылками.
  • grafon_call_graph — кто вызывает метод и кого вызывает он.
  • grafon_find_subscriptions — все подписки на событие объекта.
  • grafon_query_usage — где используется конкретный регистр или реквизит.

Минимальный набор из пяти тулов закрывает 95% задач рефакторинга и отладки.

Сценарии, где AST-слой критичен

Рефакторинг общего модуля

Переименование ОбщегоНазначения.ПолучитьОбщийМакет в конфигурации с 4000 вызовов без графа — это поиск по тексту и ручная проверка. С графом агент получает точный список узлов с номерами строк и правит точечно.

Анализ подписок на события

Подписки (ПередЗаписью, ПриПроведении, ПриИзменении) разбросаны по конфигурации и не видны из модуля объекта. Граф строит обратные рёбра и показывает всю цепочку.

Разбор сложных запросов

AST помечает тексты запросов как отдельные узлы. Агент видит, какие поля метаданных задействованы, и может предложить оптимизацию индексов или переписать соединение.

Внедрение нового функционала в чужую конфигурацию

Разработчик получает не «весь модуль менеджера», а список точек расширения и существующих паттернов. Это снижает риск нарушить типовую логику.

Ограничения и правила гигиены контекста

  1. AST не понимает динамический код. Конструкции с Выполнить() и Вычислить() остаются «тёмными» — их лучше явно исключать из среза.
  2. Глубину среза надо ограничивать. depth: 3 и выше резко возвращает объём. Начните с depth: 1–2.
  3. Индексируйте после мержа. Инкрементальное обновление дешевле полной пересборки, но требует корректных настроек наблюдения за файлами.
  4. Не смешивайте версии. Граф должен соответствовать рабочей копии, иначе агент получит сигнатуры из другой ветки.

Итог

AST-парсер BSL — это не оптимизация, а необходимое условие работы ИИ-агента с большой конфигурацией 1С. Без него любая модель захлёбывается в XML и BSL. С ним агент получает ровно тот срез метаданных и кода, который нужен для конкретной задачи: сигнатуры, связи, точки расширения.

Графон реализует эту схему как локальный индекс и MCP-сервер, подключаемый к Claude Code, Cursor и Windsurf. Экономия токенов до 10 раз, ускорение ответа в 5 раз, предсказуемое поведение агента без галлюцинаций — при полном сохранении исходников на машине разработчика.