Как исправить задвоение строк и некорректные единицы измерения в отчете по перемещению товаров в 1С:УТ 11

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

При разработке отчетов в 1С:Управление торговлей 11.4 часто возникает ситуация, когда в итоговой таблице начинают дублироваться строки номенклатуры или подтягиваются странные единицы измерения, которые не соответствуют действительности. Особенно это актуально для сложных запросов, где соединяются документы перемещения, поступления и регистры цен. Разберем по шагам, почему это происходит и как правильно сконструировать запрос, чтобы получить корректные данные.

Анализ структуры запроса и причин задвоения

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

Проанализируем, почему такая конструкция ошибочна. В системе 1С при использовании конструкции выбора вложенной таблицы в плоском запросе происходит конфликт механизмов выборки. Если мы одновременно делаем соединение с табличной частью и просим систему выдать эту же табличную часть как вложенную таблицу в одной строке, платформа может продублировать записи для каждой строки из соединения. Выясним причину появления разных единиц измерения: в конфигурациях на базе ERP-платформы (УТ 11, КА 2, ERP) у номенклатуры есть Единица хранения и могут быть Упаковки. Если в запросе обращаться к Номенклатура.ЕдиницаИзмерения, мы всегда будем получать базовую единицу, но в регистре цен или в табличной части документа могут быть зафиксированы упаковки (например, «метры» вместо «штук»), что и создает иллюзию задвоения с разными единицами.

Правильное построение запроса от табличной части

Вместо того чтобы начинать запрос от «шапки» документа (ссылки), мы должны строить его от основной аналитической единицы — строки табличной части. Это позволит нам получить плоскую таблицу без лишних вложенных циклов. Посмотрим на пример правильной структуры запроса:


ВЫБРАТЬ
    ПеремещениеТовары.Ссылка КАК ДокументПеремещения,
    ПеремещениеТовары.Номенклатура КАК Номенклатура,
    ПеремещениеТовары.Номенклатура.ЕдиницаИзмерения КАК ЕдИзмБазовая,
    ПеремещениеТовары.Упаковка КАК ЕдИзмДокумента,
    ПеремещениеТовары.Количество КАК Количество,
    ПеремещениеТовары.Ссылка.СкладПолучатель КАК СкладПолучатель,
    ПеремещениеТовары.Ссылка.ДокументОснование КАК Поступление,
    Цены.Цена КАК ЦенаЗакупки
ИЗ
    Документ.ПеремещениеТоваров.Товары КАК ПеремещениеТовары

Обратим внимание на важный момент: обращаясь напрямую к Документ.ПеремещениеТоваров.Товары, мы получаем доступ ко всем реквизитам «шапки» через поле Ссылка. Это исключает необходимость в лишних соединениях (JOIN) между документом и его табличной частью, что положительно сказывается на производительности и исключает логические ошибки дублирования строк.

Оптимизация работы с регистрами цен

Часто в подобных отчетах требуется получить цену на момент совершения операции. В исходном примере использовалась виртуальная таблица СрезПервых. Однако для управленческих отчетов чаще требуется именно актуальная цена на дату документа, что обеспечивается таблицей СрезПоследних.

Разберем типичные ошибки при соединении с регистром цен:

  1. Отсутствие фильтра по виду цены: В УТ 11 для одной номенклатуры может быть создано множество цен (закупочная, розничная, дилерская). Если не указать конкретный ВидЦены в параметрах виртуальной таблицы или в условии соединения, запрос выдаст столько строк по одной позиции номенклатуры, сколько видов цен для нее задано. Это одна из главных причин «задвоения».
  2. Использование СрезПервых: Данная таблица возвращает самую первую запись в истории, что редко имеет смысл для текущих перемещений. Используем СрезПоследних и передаем в параметры дату документа.

Рассмотрим, как правильно настроить соединение с ценами:


ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.ЦеныНоменклатуры.СрезПоследних(&Период, ВидЦены = &НужныйВидЦены) КАК Цены
ПО ПеремещениеТовары.Номенклатура = Цены.Номенклатура

Проблема производительности: обращение через точку к Регистратору

В процессе анализа кода мы можем встретить обращение типа Цены.Регистратор.Дата. Проанализируем ситуацию: поле Регистратор в регистрах сведений является составным типом (оно может ссылаться на десятки видов документов). Когда мы пишем .Дата, платформа 1С на уровне SQL-запроса выполняет LEFT JOIN со всеми таблицами документов, которые могут быть регистраторами для этого регистра. Это катастрофически замедляет выполнение отчета.

Для оптимизации рекомендуется использовать поле Период самого регистра, которое в 99% случаев совпадает с датой регистратора, но уже проиндексировано и доступно без обращений к другим таблицам. Если же вам критически нужна дата именно документа-регистратора, лучше сначала выбрать данные во временную таблицу, а затем соединить её с конкретной таблицей нужного типа документа.

Итоговые рекомендации по исправлению отчета

Для того чтобы отчет по перемещениям работал корректно и быстро, придерживаемся следующих правил:

  1. Используем плоскую структуру: Основной источник данных — Документ.ПеремещениеТоваров.Товары. Выкидываем все конструкции вида ПеремещениеТоваров.Товары.(...) из текста запроса.
  2. Контролируем единицы измерения: Если нам нужна единица из документа, берем поле Упаковка. Если нужна базовая единица товара — Номенклатура.ЕдиницаИзмерения. Никогда не смешиваем их в одном поле без приведения к общему коэффициенту (через поле Коэффициент).
  3. Фильтруем цены: При соединении с регистром ЦеныНоменклатуры обязательно накладываем условие на ВидЦены. Это предотвратит размножение строк.
  4. Убираем лишние связи: Не соединяйте Документ.ПеремещениеТоваров с его ТЧ вручную, если в этом нет специфической необходимости. Доступ к реквизитам документа через Товары.Ссылка.Дата работает эффективнее и надежнее.

Соблюдение этих архитектурных правил позволит вам создавать чистые, быстрые и, самое главное, достоверные отчеты в системе 1С:Предприятие.

← На главную