К содержанию
IFC-RS
Viewer English
Wiki проекта ru

MCP — technology preview

MCP не входит в стабильный Core 0.3. ifc-mcp содержит независимые от транспорта семантические read-only запросы, а ifc-mcp-server — локальный JSON-RPC/MCP stdio-адаптер. В ядре нет LLM-клиента, учётных данных и сетевого транспорта.

Доступные инструменты сервера

Семантические этапы 1–2 используют ifc-mcp-server.dto.v3:

  • open_model — открыть IFC, определить официальную схему и один раз построить переиспользуемые индексы;
  • close_model — идемпотентно закрыть модель и освободить исходные байты, индексы и диагностики;
  • model_info — схема IFC, ревизия, размер, число сущностей, краткая пространственная сводка, назначения единиц и сводка диагностик;
  • model_diagnostics — ограниченная страница диагностик с фильтрами severity/code;
  • search_entities — поиск по IFC-типам и подтипам, имени, GlobalId и пространственному контейнеру;
  • get_spatial_tree — страница пространственных узлов с сохранением родительских связей;
  • get_elements_in_container — элементы контейнера напрямую или рекурсивно;
  • get_entity — семантическая карточка сущности;
  • get_entity_raw — отдельная исходная STEP-запись.

До следующих этапов сохранены прежние get_properties и get_relations, а также IDS-инструменты. model_summary и find_entities больше не рекламируются; прежнее raw-поведение get_entity перенесено в get_entity_raw.

Диагностики ограничиваются ещё во время сбора: при полном проходе сохраняется точный счётчик, а при исчерпании bounded validation work summary явно помечается как неполная; материализованные details не превышают server limit. Маркер diagnostics_truncated сохраняется независимо от severity/code filters. Name читается по позиции из EXPRESS metadata, GlobalId применяется только к потомкам IfcRoot; перед созданием owned-строки semantic projection проверяет официальный предел IfcGloballyUniqueId в 22 байта, а oversized malformed значение остаётся доступно через raw STEP. casefold_exact/contains используют полный Unicode case folding. get_entity отдельно декодирует только Name, Description и PredefinedType с query budget/deadline. Неизвестный IFC-тип и malformed Name возвращают typed errors. Для raw STEP размер source range проверяется до копирования; encoded lossy/JSON размер оценивается без создания полной строки, а не-UTF-8 байты остаются доступны через lossy UTF-8 projection с символом замены. Summary-списки model_info прекращают сбор после контрольного элемента сверх лимита и используют общий entity budget/deadline; отсутствующий в активной схеме IfcFacility не запускает model scan. Scanner DiagnosticsLimit всегда делает diagnostic total нижней границей и сохраняет маркер усечения. close_model проверяет размер ответа до освобождения модели. Успешное закрытие и ошибки open_model/close_model входят в корневую JSON Schema DTO v3; lifecycle ошибки возвращают стабильный diagnostic code без фиктивной ревизии модели. Полная проверка модели без query indexes строит один компактный type lookup и не повторяет линейный поиск для каждой IFC-ссылки. Stage 1 удерживает bounded профиль Express ID/type/GlobalId/reference/Pset-Qto, чтобы сохранённые get_properties и get_relations не возвращали ложные пустые ответы. max_index_bytes ограничивает индексы; общий registry budget дополнительно учитывает capacity source, scanner/type metadata, полный EXPRESS AST, model caches, диагностики и session allocation. Нехватка памяти для обязательного индекса или полной retained session прерывает открытие, а rollback/close освобождают полный charge. Malformed IFC type проверяется до owned-copy и отображается коротким <invalid_ifc_type>, сохраняя доступ к raw STEP. Model-bound string prechecks используют DTO v3 error envelope. max_response_entities ограничивает общий набор ссылок model_info и запрошенную страницу поиска.

Контракт запросов

open_model принимает schema + path + context, close_modelschema + model_id + context. Остальные запросы принимают:

{
  "schema": "ifc-mcp-server.dto.v3",
  "model_ref": {
    "model_id": 1,
    "expected_revision": 0
  },
  "arguments": {},
  "context": {
    "request_id": "request-1",
    "budget": {
      "max_entities_scanned": 100000,
      "max_values_decoded": 100000,
      "max_relation_expansions": 100000,
      "max_response_bytes": 1048576,
      "soft_timeout_ms": 5000
    }
  }
}

Поиск возвращает не более 1 000 элементов на страницу. Курсор связан с tool, моделью, ревизией и полным нормализованным запросом. Пространственные фильтры container, storey_id, space_id поддержаны. Материальные, классификационные и property-фильтры отклоняются до этапа 3, а не игнорируются.

Лимиты по умолчанию: 512 MiB на модель, 8 открытых моделей, Express ID до 10 000 000, 4 KiB на строковый аргумент, 10 000 сохранённых диагностик/ID и 1 MiB на входной кадр. Ответ дополнительно ограничен бюджетом запроса.

Запуск

cargo build --release -p ifc-mcp-server
./target/release/ifc-mcp-server

Пример конфигурации MCP-клиента:

{
  "mcpServers": {
    "ifccore": {
      "command": "/absolute/path/target/release/ifc-mcp-server",
      "args": []
    }
  }
}

Сервер может читать любой файл, доступный его пользователю ОС. Ограничьте права процесса и рабочий каталог: сетевую песочницу сервер не создаёт. Подробности: MCP preview.

Семантический Stage 3

Добавлены get_entity_relations, get_materials, get_quantities и v3-формы get_property/get_properties. Legacy-формы и IDS family сохранены. Значения содержат IFC datatype, единицы, независимые происхождение/владение и точный association path; одноимённые instance/type значения перечисляются отдельно. Поиск поддерживает material/classification/property predicates до пагинации, с cumulative budget и filter_coverage (material → classification → properties). get_quantities не подменяет Qto геометрией.

Preview поддерживает скалярные attributes, IfcPropertySingleValue, complex containers и простые Qto. Остальные property/aggregate kinds, неизвестные relation kinds и неподдержанные единицы завершаются типизированной ошибкой. Подробности, формы запросов и приёмочные тесты: MCP technology preview. Viewer, запись IFC и deployment не меняются.

Stage 6: семантические adapters

Первый последовательный блок добавляет get_entity_location, get_related_entities, find_by_property, find_by_material, material_summary, quantity_coverage, summarize_entities поверх общих Stage 1–4 engines. Все они используют model/revision-aware DTO v3 и остаются read-only. Геометрия, временные Viewer sessions и Stage 5 preview release не объявляются готовыми наличием этих adapters. Актуальные ограничения и приёмка: канонический план.

Stage 6: геометрические запросы

Добавлены get_bounding_box, get_geometry_metrics, query_elements_in_box. Они используют существующий ifc-geometry, а не значения Qto; происхождение помечено computed_geometry. Координаты ifc_model_world учитывают placements, но не означают геореференсированную CRS. Единица берётся из project UnitsInContext; отсутствие, неоднозначность и неподдержанная length unit дают явную ошибку, а не молчаливое предположение метров.

Профиль ограничен 50 000 записями, 4 MiB исходного диапазона, 1 000 продуктами, 200 000 треугольниками, 64 MiB geometry и 128 развёрнутыми mesh-объектами. Пользователь может только уменьшить эти пределы. До построения pipeline проверяется вся модель; для decode/relation budget применяется консервативная оценка source bytes × число продуктов. Большая модель может быть отклонена, даже если выбран один простой элемент. Это ограничение preview, а не SLA. Синхронная extraction не имеет cooperative cancellation: мягкий deadline проверяется до/после вызова, geometry engine сохраняет собственные hard limits.

AABB query использует общий EntityFilter, затем пересечение мировых AABB; это не точное пересечение solid с областью. Неподдержанный либо частичный Body не становится нулевым bbox. Метрики вычисляются по tessellated mesh; значения для непроверенной топологии недоступны с причиной. Объём нескольких mesh не объявляется объёмом их объединения. Точность зависит от tessellation ядра.

ifc-geometry — уже существующая внутренняя зависимость workspace с лицензией проекта. Стандартная библиотека не предоставляет IFC tessellation. Новые внешние пакеты не добавлены; MCP crate получает geometry dependency, stable facade API и существующий Viewer не меняются. Геометрическое ядро поддерживает WASM, но этот adapter принимается отдельно от стабильного WASM-релиза.

Приёмка: stage6_geometry (IFC2X3/IFC4/IFC4X3, placements, единицы, budgets, cursors) и реальный stdio-сценарий синтетической модели двух параллелепипедов. Локальные Viewer-сессии реализованы отдельным opt-in блоком ниже.

Stage 6: локальные Viewer-сессии — реализовано

create_viewer_session, update_viewer_selection, close_viewer_session доступны в MCP DTO v3. По умолчанию backend выключен и возвращает viewer_disabled. Включение разрешено только host при запуске:

ifc-mcp-server --enable-local-viewer

MCP transport остаётся stdio. Дополнительный HTTP listener привязан только к 127.0.0.1 на случайном порту и отдаёт read-only HTML/mesh/selection. Viewer не публикует исходные IFC, filesystem paths или операции редактирования. Нет CDN и hosted upload. Браузер должен работать на том же компьютере, что и MCP server; loopback URL удалённой ВМ не является публичной ссылкой.

Create принимает либо entity_ids (до 16), либо общий filter, а также selection, ttl_seconds (1–900, по умолчанию 300) и geometry limits. Превышение 16 выбранных фильтром сущностей отклоняется, а не усекается. Все выбранные объекты должны иметь поддержанную геометрию. Ответ: viewer_session_id, url, model_id, model_revision, ttl_seconds. Update принимает viewer_session_id и selection; close — только handle. Все вызовы используют обязательный model_ref и сначала проверяют revision.

URL содержит случайный 256-битный bearer token в fragment. Браузер удаляет его из адресной строки и передаёт в Authorization; Host, Origin, Sec-Fetch-Site, CSP, no-store и no-referrer ограничивают browser boundary. Token даёт доступ к сцене любому локальному клиенту, который им владеет: это capability, не аутентификация пользователя ОС и не multi-tenant sharing. Actor boundary — экземпляр stdio server; чужой process manager не разделяет его session store.

Максимум 4 сессии, 8 MiB сериализованной сцены и 16 MiB суммы JSON payloads. Дополнительно удерживаются типизированные mesh buffers и ограниченные временные копии при сериализации/HTTP-ответе; JSON quota не заявляется как полный RSS. Исходные IFC-копии и временные файлы сессий не создаются. TTL timer очищает сессии без HTTP-трафика; close/close_model отзывают ссылки и освобождают сохранённую сцену. Уже начатый HTTP-ответ может завершиться после отзыва; следующие запросы получают 410. Lifecycle lock исключает создание новой сцены параллельно закрытию модели. Браузер очищает canvas/GPU buffers при отзыве, истечении срока или недоступности endpoint.

Приёмка: unit security/lifecycle tests, реальный MCP stdio open/create/update/ close/close_model и scripts/test-mcp-viewer-session.mjs с Chromium. Браузерный тест открывает настоящий Rust server и IFC fixture, получает 2 mesh/24 triangles, меняет подсветку 2 → 3, проверяет орбиту, закрытие и независимый TTL. Mock HTTP не используется как доказательство сквозной приёмки.

Зависимость server-only getrandom 0.3.4 уже присутствовала в Cargo.lock; лицензия MIT OR Apache-2.0. Она нужна для системной криптографической энтропии, которой нет в portable std API. Вызывается только при создании сессии, не добавляется в transport-free MCP или stable WASM facade; количественный эффект на размер/сборку не заявляется. Hosted service и write-tools отсутствуют. Stage 5 preview release не считается завершённым реализацией Stage 6.