При работе с автоматическим OData-интерфейсом в 1С:Предприятие программисты часто сталкиваются с ситуацией, когда обращение к конкретным сущностям (например, Catalog_Клиенты) проходит успешно, но попытка получить полное описание метаданных по адресу /odata/standard.odata/$metadata возвращает стандартную «Внутреннюю ошибку OData сервиса» с кодом -1. Особенно часто эта проблема проявляется на платформе версии 8.3.24.1342 и выше в конфигурациях с режимом совместимости 8.3.17. Для быстрого формирования и проверки корректности URL к отдельным сущностям можно использовать генератор запросов к стандартному интерфейсу OData.
Рассмотрим подробно причины возникновения этой ошибки и разберем по шагам алгоритм диагностики и устранения неисправности. Проанализируем ситуацию комплексно: от настроек прав доступа до специфических багов платформы и ограничений веб-серверов.
Первое, что мы должны сделать при получении ошибки с кодом -1 — это перестать гадать и обратиться к первоисточнику информации. Сообщение «Дополнительные сведения можно найти в технологическом журнале» — это прямой призыв к действию. Рассмотрим, как правильно настроить сбор логов для локализации проблемы OData.
Нам необходимо создать файл logcfg.xml в каталоге настроек платформы (обычно это C:\Program Files\1cv8\conf). Для отладки сервиса OData нам интересны события исключительных ситуаций EXCP и события работы веб-сервисов. Проанализируем пример настройки:
<config xmlns="http://v8.1c.ru/7.4/config/log">
<log location="C:\logs\odata_error" history="24">
<event>
<eq property="Name" value="EXCP"/>
</event>
<event>
<eq property="Name" value="HASP"/>
</event>
<property name="AllProperties"/>
</log>
</config>
После настройки ТЖ повторим запрос к $metadata в браузере. В логах ищем записи с тегом Context, содержащие OData. Чаще всего там обнаруживается ошибка типа MetadataException или уточнение о том, что какой-то объект метаданных не найден в составе интерфейса, хотя на него ссылается другой, опубликованный объект.
Разберем одну из самых коварных причин: конфликт ссылочных типов. Когда мы публикуем объект (например, документ) в составе OData, платформа пытается построить XML-схему всех его реквизитов. Если один из реквизитов имеет составной тип данных, включающий объект, который не включен в состав OData-интерфейса, генератор метаданных может выдать ошибку при формировании общего словаря. В случаях сложной миграции между базами можно использовать перенос данных с сопоставлением по произвольным полям поиска, чтобы не зависеть от идентичности ссылок и состава опубликованных метаданных.
Проанализируем наши действия по проверке состава:
ХранилищеЗначения. OData не умеет отдавать их «в лоб» внутри общей схемы, и иногда их наличие приводит к сбоям генерации метаданных.ЛюбаяСсылка. Если в конфигурации есть такие реквизиты, платформа обязана включить в $metadata описания всех возможных типов, что часто приводит к рекурсивным ошибкам или превышению лимитов памяти.Поскольку запрос к конкретному справочнику работает, а к общему списку метаданных — нет, мы можем сделать вывод, что проблема в объеме данных. Файл $metadata для крупной конфигурации может весить 20, 50 или даже 100 МБ. Стандартные настройки веб-серверов часто не рассчитаны на передачу таких XML-файлов одним куском.
Если мы используем IIS, проверим параметр maxAllowedContentLength. Рассмотрим, как его изменить в файле web.config, который находится в папке с публикацией базы:
<system.webServer>
<security>
<requestFiltering>
<requestLimits maxAllowedContentLength="104857600" />
</requestFiltering>
</security>
</system.webServer>
Здесь мы установили лимит в 100 МБ. Также стоит увеличить executionTimeout в секции httpRuntime, так как формирование дерева метаданных «самописной» конфигурации на платформе 8.3.24 может занимать значительное время.
Для Apache проанализируем настройки KeepAliveTimeout и LimitXMLRequestBody. Если сервер обрывает соединение до того, как 1С закончила сериализацию метаданных, клиент получит пустой ответ или внутреннюю ошибку сервиса.
Платформа 8.3.24.1342 имеет ряд зафиксированных ошибок, связанных с формированием имен в OData. Рассмотрим ситуацию: у вас есть два объекта, имена которых при транслитерации в латиницу (которую делает 1С для OData) начинают совпадать. Либо имя объекта содержит символы, которые некорректно обрабатываются парсером XML при генерации схемы.
Посмотрим на важный нюанс: в режиме совместимости 8.3.17 механизмы сериализации работают по старым алгоритмам, но сама платформа 8.3.24 пытается использовать новые оптимизированные методы. Это создает «вилку» в логике работы. Попробуем выполнить следующие действия:
Иногда внутренняя ошибка возникает из-за того, что кэш метаданных OData на стороне сервера приложений 1С «протух» или содержит некорректные ссылки после динамического обновления конфигурации. Разберем по шагам процедуру «жесткого» сброса:
Этот метод кажется радикальным, но он позволяет гарантированно очистить внутренние соответствия идентификаторов OData и объектов метаданных 1С. После восстановления стабильной работы интерфейса и выполнения синхронизации рекомендуется сравнить бухгалтерские и налоговые проводки между базами, чтобы проконтролировать корректность переданных данных.
Проанализируем права пользователя, под которым осуществляется подключение. Даже если у пользователя установлены «Полные права», в современных версиях платформы этого может быть недостаточно для корректной инициализации OData-сессии. Убедимся, что у роли включены следующие права на уровне всей конфигурации (это также актуально, если настраивается автоматический обмен данными между базами 1С по расписанию):
Запуск AutomationЗапуск внешнего соединенияУдаленный доступ (OData) (это право появилось в более поздних версиях, но в 8.3.24 стоит проверить наличие аналогичных ограничений в профилях безопасности).Если после выполнения всех описанных шагов ошибка сохраняется, рекомендуем проверить версию платформы на наличие в баг-трекере 1С записи о конкретной ошибке формирования $metadata. В ряде случаев помогает только обновление на более стабильный патч-релиз (например, переход с 1342 на более свежие сборки 8.3.24).