Почему не работает отбор «Не равно» по сегменту партнеров в отчетах 1С и как это исправить?

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

При работе с типовыми конфигурациями на платформе «1С:Предприятие 8» (такими как «1С:ERP Управление предприятием», «1С:Комплексная автоматизация» или «1С:Управление торговлей») пользователи и аналитики часто сталкиваются со странным поведением отчетов. Типичный пример: необходимо построить отчет по задолженности клиентов, исключив из него определенную группу — например, безнадежных должников, которые были вручную объединены в сегмент «Должники».

Логичным действием кажется установка в настройках отчета простого фильтра: Сегмент партнеров — Не равно — Должники. Однако на практике такой отбор не срабатывает: отчет продолжает выводить абсолютно всех контрагентов, включая тех, кто входит в исключаемый сегмент. При этом отбор на равенство (Равно) отрабатывает безупречно. Выясним техническую причину этой проблемы и подробно разберем несколько эффективных способов ее решения.

Почему логика условий «Не равно» и «Не в списке» ломается в СКД при работе с сегментами?

Для того чтобы понять природу этой ошибки, проанализируем внутреннее устройство механизма сегментации в типовых решениях 1С. Запрос стандартного отчета не обращается напрямую к справочнику Партнеры с проверкой их сегментов «на лету». Вместо этого Система компоновки данных (СКД) использует оптимизированный алгоритм связи с регистром сведений ПартнерыСегмента.

При формировании отчета СКД выполняет следующие действия:

  1. Создание временной таблицы отбора: Система обращается к регистру РегистрСведений.ПартнерыСегмента и выбирает из него всех партнеров, которые соответствуют заданному условию. Полученный массив данных сохраняется во временную таблицу (например, ВТ_ОтборПоСегменту).
  2. Накладывание жесткого фильтра на основной запрос: В основном запросе, который выбирает остатки взаиморасчетов, происходит соединение с этой временной таблицей. В итоговую выборку попадают только те записи, партнеры по которым присутствуют во временной таблице.

Когда мы пытаемся применить условие Сегмент НЕ РАВЕН "Должники", этот стройный алгоритм приводит к двум критическим логическим ошибкам:

Именно из-за этих архитектурных особенностей разработчики фирмы «1С» закладывали использование отборов по сегментам в СКД исключительно на равенство (операторы Равно или В списке). Любые попытки инвертировать отбор стандартными средствами настройки компоновки обречены на неудачу.

Рассмотрим детально, как обойти эту проблему без изменения кода конфигурации.

---

Решение 1. Метод «Сегмент от обратного» (Рекомендуемый аналитический подход)

Поскольку механизм СКД безошибочно работает с условием Равно, мы можем решить задачу от обратного. Для этого нам необходимо создать новый сегмент, который будет включать только «разрешенных» для вывода в отчет клиентов.

Разберем этот процесс по шагам:

  1. Перейдем в раздел CRM и маркетинг — Настройки и справочники — Сегменты клиентов.
  2. Создадим новый сегмент с понятным названием, например: Клиенты без безнадежных долгов.
  3. В поле Способ формирования выберем значение Периодически обновлять или Формировать динамически.
  4. Нажмем кнопку Настроить правила спроса/формирования. Перед нами откроется конструктор схемы компоновки данных сегмента.
  5. В схеме компоновки добавим левое соединение со справочником партнеров или установим отбор по вхождению в сегменты. Нам нужно задать следующее условие отбора: Партнер.Ссылка НЕ В ИЕРАРХИИ (Сегмент "Должники") или использовать встроенный механизм исключения сегментов в настройках компоновки правила сегмента.
  6. Сохраним настройки и нажмем кнопку Сформировать в карточке сегмента (если выбран периодический способ формирования).
  7. Теперь откроем наш стандартный отчет «Задолженность клиентов». В настройках отчета (раздел «Фильтры» или через «Изменить вариант отчета») установим условие: Сегмент клиентов — Равно — Клиенты без безнадежных долгов.

Данный метод абсолютно надежен, не требует программирования и работает на стандартных механизмах платформы.

---

Решение 2. Использование механизма дополнительных реквизитов

Сегменты в концепции ERP-систем представляют собой динамические маркетинговые списки. Для фиксации статических системных признаков клиентов (таких как запрет на отгрузку, статус надежности или необходимость исключения из отчетности) гораздо правильнее использовать дополнительные реквизиты.

Посмотрим, как быстро настроить этот функционал:

  1. Перейдем в меню НСИ и администрирование — Общие настройки — Дополнительные реквизиты и сведения.
  2. В списке найдем справочник Партнеры (или Контрагенты) и добавим для него новый дополнительный реквизит.
  3. Зададим имя реквизита: Исключить из отчетов по задолженности. Тип значения выберем Булево (Да/Нет).
  4. Зайдем в карточки тех клиентов, долги которых мы хотим скрыть, и установим для этого реквизита флаг в положение Да.
  5. Откроем отчет «Задолженность клиентов» и перейдем в расширенные настройки. Добавим новый отбор. Через точку от поля Клиент (или Партнер) найдем наш дополнительный реквизит: Партнер.[Исключить из отчетов по задолженности].
  6. Установим вид сравнения: Равно — Нет.

Поскольку дополнительный реквизит является свойством самого объекта базы данных (а не элементом стороннего регистра сведений с уникальными связями), СКД при таком отборе корректно обработает значения NULL (когда реквизит не заполнен вовсе). В отчет попадут все клиенты, кроме тех, у кого флаг установлен принудительно.

---

Решение 3. Методологическое списание безнадежной задолженности

Проанализируем ситуацию с точки зрения ведения бухгалтерского и управленческого учета. Если клиенты из списка «никогда не вернут долги», то отражение этих сумм в качестве активной дебиторской задолженности искажает реальную финансовую картину предприятия (активы компании выглядят переоцененными).

Наиболее правильным решением будет официальное признание долга безнадежным и его последующее списание:

  1. Перейдем в раздел Казначейство (или Взаиморасчеты) и создадим документ Корректировка задолженности (в зависимости от релиза КА название может быть Списание задолженности).
  2. Выберем тип операции Списание дебиторской задолженности.
  3. Заполним табличную часть списком наших безнадежных должников и суммами их долга.
  4. В качестве статьи расходов/активов укажем статью списания (например, «Прочие расходы» или спишем за счет ранее созданного резерва по сомнительным долгам).
  5. Проведем документ.

После проведения документа баланс взаиморасчетов с данными контрагентами обнулится. Они автоматически перестанут выводиться в любых отчетах по задолженности, без необходимости настраивать сложные фильтры и поддерживать актуальность ручных сегментов.

---

Решение 4. Доработка через расширение конфигурации (для программистов)

Если по каким-то причинам бизнес-логика требует использовать именно отрицание по сегментам во многих отчетах сразу, и ручная настройка обходных путей не подходит, мы можем прибегнуть к программной корректировке.

Чтобы сохранить конфигурацию на поддержке, создадим расширение. Нам потребуется переопределить обработку компоновки данных. Типовой общий модуль, отвечающий за подготовку отчетов перед выводом (например, КомпоновкаДанныхКлиентСервер или специализированные модули отчетов), содержит процедуры формирования текстов запросов СКД.

Мы можем перехватить процедуру компоновки и программно заменить стандартный отбор по сегменту на конструкцию вида:


// Пример модификации отбора в процедуре ПриКомпоновкеРезультата
Для Каждого ЭлементОтбора Из КомпоновщикНастроек.Настройки.Отбор.Элементы Цикл
    Если ТипЗнч(ЭлементОтбора) = Тип("ЭлементОтбораКомпоновкиДанных") 
        И ЭлементОтбора.ЛевоеЗначение = Новый ПолеКомпоновкиДанных("Партнер.Сегмент") 
        И ЭлементОтбора.ВидСравнения = ВидСравненияКомпоновкиДанных.НеРавно Тогда
        
        // Перестраиваем логику отбора на использование отрицания вхождения в список
        ЭлементОтбора.Использование = Ложь;
        НовыйОтбор = КомпоновщикНастроек.Настройки.Отбор.Элементы.Добавить(Тип("ЭлементОтбораКомпоновкиДанных"));
        НовыйОтбор.ЛевоеЗначение = Новый ПолеКомпоновкиДанных("Партнер");
        НовыйОтбор.ВидСравнения = ВидСравненияКомпоновкиДанных.НеВСписке;
        НовыйОтбор.ПравоеЗначение = ПолучитьМассивПартнеровСегмента(ЭлементОтбора.ПравоеЗначение);
        НовыйОтбор.Использование = Истина;
    КонецЕсли;
КонецЦикла;

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

Резюме

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

← На главную