При интеграции двух информационных баз 1С:Предприятие часто возникает задача быстрой передачи структурированных данных без необходимости детального описания сложных схем XDTO или ручной сборки JSON. Наиболее компактным и быстрым способом в рамках экосистемы 1С является передача сериализованной таблицы значений (ТаблицаЗначений).
Рассмотрим подробно, как правильно упаковать таблицу значений на стороне HTTP-сервиса, отправить её клиенту и корректно восстановить на принимающей стороне.
Разберем базовый способ, в котором таблица значений упаковывается во внутренний бинарный формат платформы со сжатием, преобразуется в строку формата Base64 с помощью функции XMLСтрока, а на принимающей стороне восстанавливается функцией XMLЗначение.
Шаг 1. Формирование ответа в методе HTTP-сервиса
На стороне источника данных создаем объект ХранилищеЗначения с максимальным уровнем сжатия и конвертируем его в строку:
// Формируем упакованную строку Base64
Хранилище = Новый ХранилищеЗначения(ТаблицаЗначений, Новый СжатиеДанных(9));
ТекстBase64 = XMLСтрока(Хранилище);
HTTPОтвет = Новый HTTPСервисОтвет(200);
HTTPОтвет.Заголовки.Вставить("Content-Type", "text/plain; charset=utf-8");
HTTPОтвет.УстановитьТелоИзСтроки(ТекстBase64);
Возврат HTTPОтвет;
Шаг 2. Получение и восстановление таблицы значений на клиенте
Для восстановления исходного объекта на стороне базы-приемника используем глобальную функцию XMLЗначение, передав ей тип Тип("ХранилищеЗначения"):
HTTPОтвет = Соединение.Получить(HTTPЗапрос);
Если HTTPОтвет.КодСостояния = 200 Тогда
СтрокаОтвета = HTTPОтвет.ПолучитьТелоКакСтроку();
// Восстанавливаем объект ХранилищеЗначения из строки XML/Base64
Хранилище = XMLЗначение(Тип("ХранилищеЗначения"), СтрокаОтвета);
// Извлекаем исходную таблицу значений
ТаблицаЗначений = Хранилище.Получить();
КонецЕсли;
Проанализируем производительность предыдущего способа: вызов функции XMLСтрока оборачивает сжатые бинарные данные в строку Base64, что увеличивает объем сетевого трафика примерно на 33% и создает дополнительную нагрузку на процессор и оперативную память. Если обе стороны обмена работают на 1С, эффективнее передавать двоичные данные напрямую без промежуточного преобразования в текст.
Посмотрим на пример реализации прямой бинарной передачи:
На стороне HTTP-сервиса (отправка):
Хранилище = Новый ХранилищеЗначения(ТаблицаЗначений, Новый СжатиеДанных(9));
ДвоичныеДанные = Хранилище.ПолучитьДвоичныеДанные();
HTTPОтвет = Новый HTTPСервисОтвет(200);
HTTPОтвет.Заголовки.Вставить("Content-Type", "application/octet-stream");
HTTPОтвет.УстановитьТелоИзДвоичныхДанных(ДвоичныеДанные);
Возврат HTTPОтвет;
На стороне клиента (прием):
HTTPОтвет = Соединение.Получить(HTTPЗапрос);
Если HTTPОтвет.КодСостояния = 200 Тогда
ДвоичныеДанные = HTTPОтвет.ПолучитьТелоКакДвоичныеДанные();
// Инициализируем ХранилищеЗначения напрямую из двоичных данных
Хранилище = Новый ХранилищеЗначения(ДвоичныеДанные);
ТаблицаЗначений = Хранилище.Получить();
КонецЕсли;
Выясним особенности и возможные риски, с которыми можно столкнуться при использовании объекта ХранилищеЗначения для передачи таблиц значений:
СправочникСсылка, ДокументСсылка и др.), при сериализации сохраняются их внутренние идентификаторы (GUID). Если база-приемник имеет другую структуру метаданных или ссылки не синхронизированы, при распаковке возникнут битые ссылки типа «Объект не найден». Для передачи между разнородными базами ссылки рекомендуется предварительно конвертировать в строки (GUID, код или наименование).COMОбъект, выборки результатов запроса, элементы форм). Попытка упаковать такую таблицу вызовет исключение.ХранилищеЗначения гарантированно работает между базами 1С:Предприятие. Если принимающей стороной выступает сторонняя система (сайт, сервис на Python/C#/Java), данные необходимо сериализовать в стандартный формат JSON с помощью методов ЗаписатьJSON и ПрочитатьJSON.