Как настроить автоматическую скидку 50% на каждый второй товар из сегмента в 1С:Управление торговлей 11?

Программист 1С v8.3 (Управляемые формы) 1С:Управление торговлей Управленческий учет Торговля и дистрибуция
← На главную

В розничной и оптовой торговле популярны маркетинговые акции формата «каждая вторая пара обуви/очков за полцены». При этом покупатель может выбрать абсолютно разные товары из определенной группы (сегмента), стоимость которых отличается. Главная сложность автоматизации такой задачи в «1С:Управление торговлей» версии 11.3 и 11.4 заключается в том, что система должна не просто посчитать количество, а корректно определить, к каким именно позициям применить скидку (как правило, к наиболее дешевым), чтобы защитить маржинальность бизнеса и не запутать покупателя.

В этой статье мы подробно разберем, почему стандартные инструменты УТ 11 ограничивают выполнение этой задачи, и пошагово рассмотрим наиболее надежное техническое решение с использованием внешней обработки расчета скидок.

В чем сложность настройки через стандартный функционал?

Если мы попытаемся настроить акцию стандартным типом скидки «Скидка количеством» в УТ 11.3, мы столкнемся с рядом системных ограничений:

  1. Проблема разных строк: Стандартная скидка количеством отлично работает, если покупатель берет несколько единиц одного и того же товара (одна строка в документе с количеством > 1). Но если клиент выбирает три разные модели солнцезащитных очков, в корзине (или чеке ККМ) это будут три разные строки. Стандартный механизм без доработок часто игнорирует общую кратность по сегменту, если товары разбиты по строкам.
  2. Алгоритм распределения скидки: Когда система все-таки определяет, что в чеке есть несколько товаров из нужного сегмента, она пытается рассчитать общую сумму скидки (равную 50% от стоимости самого дешевого товара) и пропорционально распределить («размазать») эту сумму по всем позициям чека. В результате покупатель видит в чеке странные копейки скидки на каждый товар вместо понятной скидки 50% на конкретную (вторую) позицию.
  3. Очередность расчета по цене: Для бизнеса критически важно, чтобы скидка 50% давалась на более дешевый товар из пары. Например, если покупатель берет очки за 10 000 рублей и очки за 2 000 рублей, скидка должна примениться к очкам за 2 000 рублей. В типовом функционале УТ 11.3 управлять этим приоритетом сортировки без программирования крайне сложно.

Для реализации честного и прозрачного алгоритма «каждый второй товар из сегмента со скидкой 50%» мы рекомендуем использовать механизм подключения внешних обработок расчета скидок.

Решение: Разработка внешней обработки на базе типового шаблона

В системе 1С:Предприятие реализован гибкий механизм расширения возможностей расчета скидок с помощью внешних обработок (файлы с расширением .epf). Мы можем взять за основу демонстрационный шаблон, поставляемый фирмой 1С, и внедрить в него собственную логику распределения скидки.

Рассмотрим алгоритм создания и подключения такой обработки по шагам.

Шаг 1. Получение и подготовка шаблона обработки

В составе демонстрационной базы «1С:Управление торговлей» (или в каталоге шаблонов установки конфигурации) присутствует учебный файл внешней обработки СкидкаНаценкаПроцентЗаСпособДоставки.epf. Этот файл служит отличным каркасом, так как в нем уже прописаны все необходимые экспортные процедуры для интеграции с подсистемой скидок-наценок УТ 11.

Скопируем этот файл, переименуем его (например, в СкидкаКаждыйВторойТоварСегмента.epf) и откроем в конфигураторе 1С.

Шаг 2. Реализация логики расчета в модуле обработки

Нам необходимо изменить код в основной экспортной процедуре расчета. Логика нашего алгоритма должна выполнять следующие действия:

  1. Отобрать из табличной части документа (заказа или чека) только те строки, номенклатура которых входит в наш сегмент (например, «Солнцезащитные очки»).
  2. Виртуально «разложить» эти товары поштучно (если в строке количество больше 1, мы должны представить это как отдельные единицы).
  3. Отсортировать весь полученный массив поштучных товаров по цене в порядке убывания. Таким образом, самые дорогие товары окажутся в начале списка, а самые дешевые — в конце.
  4. Пройти по списку и применить скидку 50% к каждому четному элементу списка (второму, четвертому, шестому и т.д.). Так как список отсортирован по убыванию цены, скидка гарантированно применится к более дешевым товарам.
  5. Схлопнуть виртуальные строки обратно и распределить рассчитанные суммы скидок по реальным строкам табличной части документа 1С.

Проанализируем пример кода, который решает эту задачу в модуле внешней обработки:


Процедура РассчитатьСкидкиИНаценки(ПараметрыРасчета, ТаблицаСкидокНаценок) Экспорт

    // 1. Получаем таблицу товаров документа из параметров расчета
    ТаблицаТоваров = ПараметрыРасчета.ТаблицаТоваров;
    
    // Подготовим массив для поштучного учета товаров из сегмента
    МассивТоваровСегмента = Новый Массив;
    
    Для Каждого СтрокаТовара Из ТаблицаТоваров Цикл
        // Проверяем принадлежность номенклатуры к нашему целевому сегменту
        Если ПринадлежитСегменту(СтрокаТовара.Номенклатура, ПараметрыРасчета.ПолучательСкидки) Тогда
            // Раскладываем количество поштучно
            Для Счетчик = 1 По СтрокаТовара.Количество Цикл
                СтруктураШтуки = Новый Структура;
                СтруктураШтуки.Вставить("СтрокаДокумента", СтрокаТовара);
                СтруктураШтуки.Вставить("Цена", СтрокаТовара.Цена);
                СтруктураШтуки.Вставить("СкидкаСумма", 0);
                МассивТоваровСегмента.Добавить(СтруктураШтуки);
            EndЦикла;
        КонецЕсли;
    КонецЦикла;
    
    // 2. Сортируем полученный массив по цене по убыванию
    // Для этого можно использовать вспомогательную таблицу значений
    ТЗ_Сортировки = Новый ТаблицаЗначений;
    ТЗ_Сортировки.Колонки.Добавить("ИндексМассива", Новый ОписаниеТипов("Число"));
    ТЗ_Сортировки.Колонки.Добавить("Цена", Новый ОписаниеТипов("Число"));
    
    Для Индекс = 0 По МассивТоваровСегмента.Количество() - 1 Цикл
        НоваяСтрока = ТЗ_Сортировки.Добавить();
        НоваяСтрока.ИндексМассива = Индекс;
        НоваяСтрока.Цена = МассивТоваровСегмента[Индекс].Цена;
    КонецЦикла;
    
    ТЗ_Сортировки.Сортировать("Цена Убыв");
    
    // 3. Распределяем скидку 50% на каждую вторую позицию (четную по счету)
    ПорядковыйНомер = 1;
    Для Каждого СтрокаСорт Из ТЗ_Сортировки Цикл
        // Каждый второй товар (2-й, 4-й, 6-й и т.д. по убыванию цены)
        Если ПорядковыйНомер % 2 = 0 Тогда
            ТекущийТовар = МассивТоваровСегмента[СтрокаСорт.ИндексМассива];
            // Скидка 50% от цены за единицу
            ТекущийТовар.СкидкаСумма = ТекущийТовар.Цена * 0.5;
        КонецЕсли;
        ПорядковыйНомер = ПорядковыйНомер + 1;
    КонецЦикла;
    
    // 4. Переносим рассчитанные скидки обратно в таблицу результатов
    Для Каждого Элемент Из МассивТоваровСегмента Цикл
        Если Элемент.СкидкаСумма > 0 Тогда
            СтрокаСкидки = ТаблицаСкидокНаценок.Добавить();
            СтрокаСкидки.КлючСвязи = Элемент.СтрокаДокумента.КлючСвязи;
            СтрокаСкидки.Сумма = Элемент.СкидкаСумма;
        КонецЕсли;
    КонецЦикла;

КонецПроцедуры

Функция ПринадлежитСегменту в коде выше должна проверять, входит ли товар в выбранный сегмент номенклатуры. Для этого можно использовать стандартные механизмы работы с сегментами в УТ 11, например, обращение к регистру сведений НоменклатураСегмента.

Шаг 3. Подключение обработки в базу 1С

После того как логика написана и сохранена в файле .epf, выполним интеграцию с пользовательским интерфейсом:

  1. Перейдем в раздел НСИ и администрирование -> Печатные формы, отчеты и обработки -> Дополнительные отчеты и обработки.
  2. Нажмем кнопку Добавить из файла и выберем нашу созданную обработку. Система автоматически определит её как внешний компонент расчета скидок.
  3. Запишем и закроем обработку.
  4. Перейдем в раздел CRM и маркетинг -> Скидки (наценки).
  5. Создадим новую скидку. В поле «Способ предоставления» выберем Внешняя обработка и укажем нашу загруженную обработку.
  6. В качестве получателя или уточнения условий укажем наш сегмент «Солнцезащитные очки».
  7. Установим статус скидки Действует и назначим ее на нужное индивидуальное соглашение или правила работы розничного магазина.

Теперь при расчете скидок в чеке ККМ или Заказе клиента система будет обращаться к нашему алгоритму. Программа автоматически отсортирует все добавленные очки по цене, определит более дешевые и предоставит на них скидку 50% в строгом соответствии с требованиями бизнеса.

← На главную