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