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