Как правильно передавать картинки и изображения между базами 1С при обмене данными?

Программист 1С v8.3 (Управляемые формы) IT и автоматизация бизнеса
← На главную

При организации распределенных информационных баз (РИБ) или настроенных планов обмена в 1С часто возникает задача передачи медиафайлов — например, основных изображений товаров. Начинающие разработчики иногда решают эту задачу «в лоб»: создают у элемента справочника (например, Номенклатура) реквизит ОсновноеИзображение с типом ХранилищеЗначения. Рассмотрим, почему такой подход приводит к серьезным проблемам с производительностью и как правильно организовать хранение и передачу картинок между базами 1С.

В чем заключается проблема использования реквизита типа ХранилищеЗначения

На первый взгляд добавление реквизита типа ХранилищеЗначения прямо в объект выглядит удобным, однако в механизме распределенных баз это создает сразу несколько критических архитектурных проблем:

  1. Избыточная повторная регистрация изменений. Каждый раз, когда пользователь редактирует элемент справочника (например, меняет наименование, цену или артикул), объект регистрируется к выгрузке целиком. В файл сообщения обмена попадают абсолютно все реквизиты, включая бинарные данные картинки. Даже если сама картинка не менялась, она будет каждый раз передаваться заново.
  2. Кодирование в Base64 и рост файла обмена. При формировании XML-сообщения обмена двоичные данные из ХранилищеЗначения преобразуются в текстовую строку Base64. Это приводит к увеличению объема передаваемых данных примерно на 33% по сравнению с исходным файлом.
  3. Повышенная нагрузка на оперативную память. Механизмы XML-сериализации считывают и обрабатывают строки Base64 в оперативной памяти целиком. При загрузке большой выгрузки серверный процесс rphost рискует израсходовать весь лимит доступной памяти, что приводит к завершению процесса с ошибкой недостатка памяти (Out of Memory) и «нависанию» обмена.

Вариант 1. Включение подчиненного справочника в план обмена

Самый простой и правильный подход — не хранить бинарные данные в самом элементе номенклатуры, а использовать отдельный подчиненный справочник (например, ХранилищеДополнительнойИнформации или присоединенные файлы) и просто включить его в состав состава плана обмена.

Рассмотрим преимущества этого подхода:

  1. Элемент основного справочника ссылается на картинку через ссылку СправочникСсылка.ХранилищеДополнительнойИнформации.
  2. При редактировании реквизитов товара сам файл картинки не регистрируется повторно в плане обмена, выгружается только сам элемент справочника номенклатуры.
  3. Картинка регистрируется и передается в подчиненную базу единоразово — только в момент её непосредственного создания или изменения.

Вариант 2. Оптимизация сжатия и программная авторегистрация

Если по условиям архитектуры всё же необходимо использовать ХранилищеЗначения в объекте, следует программно ограничить авторегистрацию и сжимать данные при записи.

Разберем по шагам, как это реализовать:

  1. В свойствах плана обмена для объекта отключим автоматическую регистрацию.
  2. В подписке на событие ПриЗаписи будем проверять, менялось ли именно изображение (например, по хэш-сумме MD5), и регистрировать объект вручную только при изменении данных картинки.
  3. При сохранении файла в ХранилищеЗначения обязательно укажем параметр степени сжатия:

ДвоичныеДанныеФайла = Новый ДвоичныеДанные(ПутьКФайлу);
// Используем оптимальное или максимальное сжатие данных
ХранилищеИзображения = Новый ХранилищеЗначения(ДвоичныеДанныеФайла, Новый СжатиеДанных(СжатиеДанных.Оптимальное));
ОбъектНоменклатура.ОсновноеИзображение = ХранилищеИзображения;
ОбъектНоменклатура.Записать();

Вариант 3. Использование механизма присоединенных файлов БСП

В конфигурациях, построенных на Библиотеке Стандартных Подсистем (БСП), реализован механизм подсистемы «Работа с файлами». Данный механизм позволяет хранить файлы вне базы данных — на томах сетевого диска. В таком случае в обмене передается не сам бинарный файл внутри сообщения обмена, а структура файлов передается отдельным пакетом или закачивается по требованию через HTTP-сервисы.

Рекомендации по передаче изображений

Проанализировав возможные сценарии, сформируем практические рекомендации для разработчиков:

  1. Избегайте хранения типа ХранилищеЗначения в реквизитах часто обновляемых справочников.
  2. Переносите хранение файлов в отдельный подчиненный справочник и включайте его в состав плана обмена.
  3. Ограничивайте максимальное разрешение и размер загружаемых фото до их сохранения в базу (выполняйте ресайз).
  4. Настраивайте порционный обмен (пакетирование), чтобы ограничить объем выгружаемых файлов XML за одну сессию обмена.
← На главную