При настройке обмена данными между конфигурациями 1С часто возникает задача переноса остатков не в документы, а напрямую в регистры сведений. Особенно это актуально, когда целевой регистр является независимым и периодическим. В данной статье мы разберем, как реализовать перенос остатков из регистра накопления (например, «Товары БУ» в УТП) в периодический регистр сведений «Комплексной автоматизации» (КА) с использованием инструмента «Конвертация данных 2.1».
Представим ситуацию: нам необходимо собрать остатки по складу, номенклатуре и номерам ГТД из одной базы и наполнить ими регистр сведений в другой. Сложность заключается в том, что в базе-источнике это могут быть данные регистра накопления, а в базе-приемнике — периодический регистр сведений. Для решения этой задачи мы воспользуемся механизмом Правил Выгрузки Данных (ПВД) с произвольным алгоритмом и Правил Конвертации Объектов (ПКО) с получением данных из входящих параметров.
Первым делом проанализируем структуру целевого регистра. Нам необходимо создать Правило Конвертации Объекта, где источником будет «Пусто», а приемником — наш регистр сведений. Разберем пошагово настройку свойств:
Склад, Номенклатура, НомерГТД, Количество).Период. Если его не заполнить, записи могут попасть на 01.01.0001.Теперь рассмотрим, как инициировать выгрузку. В Правилах Выгрузки Данных мы не будем использовать стандартную выборку объектов, так как нам нужно предварительно рассчитать остатки. Мы выберем способ выборки «Произвольный алгоритм».
В обработчике «Перед обработкой» напишем код, который соберет данные и вызовет выгрузку. Проанализируем пример кода:
// 1. Формируем запрос для получения остатков из источника
Запрос = Новый Запрос;
Запрос.Текст =
"ВЫБРАТЬ
| ТоварыБУОстатки.Склад КАК Склад,
| ТоварыБУОстатки.Номенклатура КАК Номенклатура,
| ТоварыБУОстатки.НомерГТД КАК НомерГТД,
| ТоварыБУОстатки.КоличествоОстаток КАК Количество
|ИЗ
| РегистрНакопления.ТоварыБУ.Остатки(&ДатаОстатков, ) КАК ТоварыБУОстатки";
Запрос.УстановитьПараметр("ДатаОстатков", КонецДня(ТекущаяДата()));
РезультатЗапроса = Запрос.Выполнить();
Выборка = РезультатЗапроса.Выбрать();
// 2. Обходим выборку и передаем данные в ПКО
Пока Выборка.Следующий() Цикл
// Создаем структуру для передачи данных
ВходящиеДанные = Новый Структура;
ВходящиеДанные.Вставить("Склад", Выборка.Склад);
ВходящиеДанные.Вставить("Номенклатура", Выборка.Номенклатура);
ВходящиеДанные.Вставить("НомерГТД", Выборка.НомерГТД);
ВходящиеДанные.Вставить("Количество", Выборка.Количество);
ВходящиеДанные.Вставить("Период", ТекущаяДата()); // Указываем дату записи
// Вызываем выгрузку по правилу
ВыгрузитьПоПравилу(,, ВходящиеДанные,, "ИмяВашегоПКО_Регистра");
КонецЦикла;
Разберем подробнее параметры функции ВыгрузитьПоПравилу. Мы передаем Неопределено в качестве объекта-источника, а в третьем параметре передаем нашу структуру ВходящиеДанные. Пятый параметр — это строковое имя ПКО, которое мы создали на первом шаге.
Если записей в регистре десятки тысяч, использование цикла с ВыгрузитьПоПравилу может замедлить процесс. Выясним причину: на каждую итерацию тратится время на инициализацию механизмов конвертации. Существует альтернативный, более быстрый способ — использование переменной ВыборкаДанных в ПВД.
В этом случае в обработчике «Перед обработкой» мы просто присваиваем результат запроса этой переменной:
Запрос = Новый Запрос("ВЫБРАТЬ ... "); // Ваш запрос
ВыборкаДанных = Запрос.Выполнить().Выгрузить();
Система сама сопоставит колонки таблицы значений с именами ПКС в правиле конвертации. Однако помните, что в ПКО все равно должны стоять флаги «Получать из входящих данных».
Рассмотрим ситуацию, когда в приемнике (базе КА) уже есть данные. Поскольку регистр независимый, новые записи с теми же измерениями просто перезапишут старые на ту же дату. Но что делать, если в источнике товар закончился, а в приемнике запись осталась? Она не будет обновлена и остатки станут некорректными.
Решение: Перед загрузкой новых данных рекомендуется очищать регистр. Это можно сделать в ПКО в обработчике «Перед загрузкой данных» на стороне приемника:
// Пример очистки регистра перед загрузкой (писать в ПКО Приемника)
Набор = РегистрыСведений.ВашРегистр.СоздатьНаборЗаписей();
// Можно установить отборы по организации или складу, если нужно
// Набор.Отбор.Склад.Установить(СкладПриемник);
Набор.Записать(Истина); // Записываем пустой набор
Проанализируем также вопрос разницы остатков. Если бухгалтерия требует записывать только изменения (дельту), вам придется в коде ПВД реализовать сравнение. Это можно сделать через COM-соединение с базой КА прямо из УТП. Вы выгружаете остатки из КА, сравниваете их в таблице значений с остатками УТП, и вычисляете разницу, которую и передаете в ВходящиеДанные.
Мы проанализировали процесс настройки переноса данных в независимый регистр сведений. Основные моменты, которые мы разобрали:
ВходящиеДанные.Период для периодических регистров.ВыборкаДанных.Применяя эти подходы, вы сможете гибко настраивать перенос любой аналитической информации между базами 1С, даже если структуры метаданных существенно различаются.