Как в измерении регистра сведений указать тип документа вместо ссылки на конкретный документ

Программист 1С v8.3 (Управляемые формы) IT и автоматизация бизнеса
← На главную

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

Разберем основные ограничения платформы 1С:Предприятие и рассмотрим проверенные способы реализации привязки настроек к типам документов.

Ограничения платформы при работе с типами данных

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

  1. Объекты Тип и ОписаниеТипов являются системными типами среды исполнения, а не ссылочными или примитивными типами базы данных. Их невозможно напрямую назначить типами реквизитов или измерений регистра.
  2. Если задать измерению составной ссылочный тип, содержащий множество видов документов, на уровне СУБД формируются дополнительные поля под идентификатор типа и смещение. Это увеличивает размер таблиц и индексов.
  3. Если попытаться выбрать документ через стандартную форму выбора ссылочного типа, когда в базе еще нет ни одного проведенного или записанного документа данного вида, список будет пустым.

Способ 1. Использование составного типа и хранение пустой ссылки

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

Разберем по шагам, как настроить измерение и обойти ограничения проверки заполнения:

  1. В конфигураторе для нужного регистра сведений открываем свойства измерения.
  2. В свойстве Тип указываем составной тип, отметив необходимые виды документов (или тип ДокументСсылка).
  3. Находим свойство Проверка заполнения и устанавливаем значение Не проверять (в обычных формах — снимаем флаг обязательного заполнения или устанавливаем свойство Возможно пустое). Это позволит платформе сохранять пустые ссылки без ошибок валидации.
  4. Для программной записи значения определенного типа в измерение передаем пустую ссылку через менеджер соответствующего документа:
    
    Менеджер = Документы.РеализацияТоваровУслуг;
    ПустаяСсылкаДокумента = Менеджер.ПустаяСсылка();
    
    Запись = РегистрыСведений.НастройкиОбработкиДокументов.СоздатьМенеджерЗаписи();
    Запись.ТипДокумента = ПустаяСсылкаДокумента;
    Запись.НастройкаАктивна = Истина;
    Запись.Записать();
    
  5. При интерактивном выборе на управляемой форме организуем выбор типа документа через список выбора или диалог выбора типа, подставляя пустую ссылку:
    
    &НаКлиенте
    Процедура ВыбратьТипДокумента(Команда)
        Оповещение = Новый ОписаниеОповещения("ПослеВыбораТипа", ЭтотОбъект);
        Диалог = Новый ДиалогВыбораТипа();
        Диалог.ВыбираемыеТипы = Новый Массив;
        Диалог.ВыбираемыеТипы.Добавить(Тип("ДокументСсылка.РеализацияТоваровУслуг"));
        Диалог.ВыбираемыеТипы.Добавить(Тип("Диалог.ПоступлениеТоваровУслуг"));
        Диалог.Показать(Оповещение);
    КонецПроцедуры
    
    &НаСервере
    Процедура УстановитьПустуюСсылкуПоТипу(ВыбранныйТип)
        // Преобразуем выбранный тип в пустую ссылку через менеджер
        ИмяОбъекта = Метаданные.НайтиПоТипу(ВыбранныйТип).Имя;
        РеквизитТипДокумента = Документы[ИмяОбъекта].ПустаяСсылка();
    КонецПроцедуры
    

Способ 2. Использование справочника «Идентификаторы объектов метаданных» (БСП)

Если конфигурация разработана на базе Библиотеки стандартных подсистем (БСП), наиболее надежным и рекомендуемым решением является использование справочника ИдентификаторыОбъектовМетаданных.

Рассмотрим преимущества и порядок работы с этим справочником:

  1. В измерении регистра указываем тип СправочникСсылка.ИдентификаторыОбъектовМетаданных. Это избавляет регистр от громоздкого составного типа и ускоряет поиск по индексу.
  2. Пользователь может выбирать метаданные через стандартную форму справочника БСП, где отображается древовидная структура всех объектов метаданных конфигурации, независимо от наличия данных в базе.
  3. В программном коде получаем идентификатор и управляем им с помощью функций общего назначения БСП:
    
    // Получение идентификатора метаданных по типу объекта
    ТипОбъекта = Тип("ДокументСсылка.РеализацияТоваровУслуг");
    Идентификатор = ОбщегоНазначения.ИдентификаторОбъектаМетаданных(ТипОбъекта);
    
    // Получение метаданных или менеджера по идентификатору
    ОбъектМетаданных = ОбщегоНазначения.ОбъектМетаданныхПоИдентификатору(Идентификатор);
    Менеджер = ОбщегоНазначения.МенеджерОбъектаПоИдентификатору(Идентификатор);
    

Способ 3. Хранение имени объекта метаданных в виде строки

Еще один универсальный вариант — хранить имя объекта (например, "Документ.РеализацияТоваровУслуг" или "РеализацияТоваровУслуг") в строковом измерении регистра.

Посмотрим на пример работы со строковыми именами метаданных:


// Запись значения
Запись = РегистрыСведений.ПравилаЗагрузки.СоздатьМенеджерЗаписи();
Запись.ИмяВидаДокумента = "РеализацияТоваровУслуг";
Запись.Записать();

// Получение метаданных и менеджера по строковому имени
МетаданныеДокумента = Метаданные.Документы.Найти(Запись.ИмяВидаДокумента);
Если МетаданныеДокумента <> Неопределено Тогда
    Менеджер = Документы[Запись.ИмяВидаДокумента];
    ПустаяСсылка = Менеджер.ПустаяСсылка();
КонецЕсли;

Как проверять и сопоставлять тип документа в запросах

Разберем, как выполнять поиск записей регистра по типу существующего документа или параметра в языке запросов 1С.

Если в регистре хранятся пустые ссылки составного типа:


ВЫБРАТЬ
    Регистр.ТипДокумента,
    Регистр.НастройкаАктивна
ИЗ
    РегистрСведений.НастройкиОбработкиДокументов КАК Регистр
ГДЕ
    // Вариант 1: Проверка на конкретный тип документа через ССЫЛКА
    Регистр.ТипДокумента ССЫЛКА Документ.РеализацияТоваровУслуг

    // Вариант 2: Сравнение типа измерения с типом переданного в параметр документа
    ИЛИ ТИПЗНАЧЕНИЯ(Регистр.ТипДокумента) = ТИПЗНАЧЕНИЯ(&ТекущийДокумент)

Для оптимизации запросов и соединений по составным типам рекомендуется приводить типы с помощью функции ТИП():


ВЫБРАТЬ
    Док.Ссылка КАК Документ,
    Настройки.НастройкаАктивна
ИЗ
    Документ.РеализацияТоваровУслуг КАК Док
    ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.НастройкиОбработкиДокументов КАК Настройки
        ПО ТИПЗНАЧЕНИЯ(Настройки.ТипДокумента) = ТИП(Документ.РеализацияТоваровУслуг)
← На главную