При работе с Библиотекой стандартных подсистем (БСП), а именно с подсистемой «Свойства», разработчики часто сталкиваются с ситуацией, когда программный интерфейс ведет себя не совсем так, как ожидается. Типичный пример: при вызове функции СвойстваОбъекта для справочника «Номенклатура» в ERP или УТ 11, массив возвращаемых свойств оказывается неполным. Рассмотрим подробнее, почему это происходит, разберем внутреннюю логику БСП и выясним, как правильно получать список доступных свойств для объектов.
Представим ситуацию в конфигурации 1С:ERP. У нас есть справочник Номенклатура. В системе настроены дополнительные реквизиты:
Программист вызывает функцию УправлениеСвойствами.СвойстваОбъекта(), передавая в нее ссылку на объект. Если объект еще не записан (пустая ссылка) или если мы пытаемся получить список всех теоретически возможных свойств, функция возвращает только «Реквизит 1». «Реквизит 2» игнорируется. Разберем, почему «сакральный смысл» этой функции отличается от простого получения метаданных.
Для того чтобы понять причину такого поведения, проанализируем фрагмент запроса, который обычно лежит в основе механизмов получения свойств в БСП (модуль УправлениеСвойствами):
ВЫБРАТЬ РАЗРЕШЕННЫЕ
ТаблицаСвойств.Свойство КАК Свойство,
ТаблицаСвойств.Значение КАК Значение,
ТаблицаСвойств.ТекстоваяСтрока,
ТаблицаСвойств.Ссылка КАК ВладелецСвойств
ИЗ
[ИмяОбъектаСоСвойствами].ДополнительныеРеквизиты КАК ТаблицаСвойств
ЛЕВОЕ СОЕДИНЕНИЕ ПланВидовХарактеристик.ДополнительныеРеквизитыИСведения КАК ДополнительныеРеквизитыИСведения
ПО ДополнительныеРеквизитыИСведения.Ссылка = ТаблицаСвойств.Свойство
ГДЕ
ТаблицаСвойств.Ссылка В (&ОбъектыСоСвойствами)
Обратим внимание на источник данных. Функция обращается напрямую к табличной части ДополнительныеРеквизиты конкретного объекта (или группы объектов). Из этого следуют важные выводы:
СвойстваОбъекта предназначена для чтения уже существующих данных в конкретном экземпляре объекта.Выясним причину, по которой «Реквизит 1» все же попадает в выборку, а «Реквизит 2» — нет. В архитектуре БСП свойства группируются в Наборы дополнительных реквизитов и сведений.
Для справочника «Номенклатура» обычно существует один общий набор (относящийся ко всему справочнику в целом) и множество специфических наборов, привязанных к конкретным значениям реквизита ВидНоменклатуры. Когда мы работаем с пустой ссылкой или объектом без заполненного вида, система видит только те свойства, которые жестко закреплены за основным набором справочника.
«Реквизит 2» не является свойством «Номенклатуры» вообще. Он является свойством Набора, который соответствует «Первому виду номенклатуры». Пока объект не связан с этим видом, БСП не считает эти свойства «его» свойствами.
Если наша задача — узнать, какие реквизиты можно заполнить для объекта (например, для программного создания карточки или динамического построения интерфейса), функция СвойстваОбъекта нам не подходит. Нам нужно действовать по другому алгоритму.
Рассмотрим шаги для получения всех доступных свойств:
УправлениеСвойствПереопределяемый.Справочник.НаборыДополнительныхРеквизитовИСведения.Пример программного получения доступных свойств для конкретного вида номенклатуры:
// 1. Получаем набор свойств, соответствующий виду номенклатуры
Наборы = Новый Массив;
Наборы.Добавить(ВидНоменклатуры.НаборСвойств); // В ERP ссылка на набор хранится в виде номенклатуры
// 2. Получаем описание всех свойств этого набора
ОписаниеСвойств = УправлениеСвойствами.СвойстваНаборов(Наборы);
// Теперь в ОписаниеСвойств содержатся метаданные всех реквизитов (и общих, и специфических)
Для Каждого Свойство Из ОписаниеСвойств Цикл
Сообщить("Доступное свойство: " + Свойство.Заголовок);
КонецЦикла;
Проанализируем ситуацию еще раз, чтобы закрепить понимание. В БСП разделены два понятия:
1. Значения свойств объекта: То, что реально записано в базе в табличной части ДополнительныеРеквизиты. Именно с этим работает СвойстваОбъекта. Если пользователь не заполнил реквизит на форме и он не имеет значения по умолчанию, строки в ТЧ может просто не быть.
2. Доступные свойства типа: Это настройки в справочнике наборов. Они определяют, какие поля должны появиться на форме. Для работы с ними используются функции СвойстваНаборов или специализированные методы из модуля УправлениеСвойствамиСлужебный.
В сложных конфигурациях типа ERP дополнительные реквизиты могут иметь условия видимости и доступности. Например, «Реквизит 2» может отображаться, только если «Реквизит 1» заполнен определенным значением. Функция СвойстваОбъекта полностью игнорирует эту логику, так как она возвращает состояние данных, а не правила интерфейса.
Если вам нужно получить список свойств с учетом их «видимости» для пользователя в текущий момент, необходимо использовать программный интерфейс, который эмулирует поведение формы:
УправлениеСвойствами.ЗаполнитьНаборыСвойствОбъекта() — для первичного определения состава наборов.Выясним краткие итоги нашего анализа:
СвойстваОбъекта для анализа «пустых» или новых объектов, если вам нужны свойства, зависящие от категории/вида/типа объекта.СвойстваНаборов, предварительно определив массив ссылок на наборы свойств.СвойстваОбъекта — это инструмент для чтения значений, а не для проектирования интерфейса.Таким образом, «сакральный смысл» функции заключается в предоставлении быстрого доступа к текущим значениям доп. реквизитов, уже привязанных к объекту в базе данных, а не в анализе всех потенциально возможных настроек системы.