При обновлении нетиповых конфигураций (например, 1С:Управление торговлей или решений на базе Библиотеки стандартных подсистем) нередко возникает ситуация, когда прикладные механизмы или платформа прерывают обновление из-за отсутствия в информационной базе предопределенных элементов. Чаще всего с этой проблемой сталкиваются при работе со справочником НаборыДополнительныхРеквизитовИСведений или планами видов характеристик.
Разберем подробнее, почему предопределенные элементы могут исчезнуть, по каким правилам платформа выполняет их автоматическое создание и какими способами можно восстановить целостность данных базы.
В платформе 1С:Предприятие 8.3 предопределенные данные физически представляют собой обычные записи в таблицах базы данных, связанные с конфигурацией через специальный реквизит ИмяПредопределенныхДанных. Если элемент был отвязан или удален в режиме предприятия, повторное создание может не произойти автоматически.
Кроме того, фактический режим обновления предопределенных данных вычисляется платформой по строгому алгоритму приоритетов:
Авто, используется именно это значение.Авто, применяется он.Авто, платформа проверяет статус базы: в периферийных узлах распределенной информационной базы (РИБ) автоматическое создание предопределенных данных по умолчанию блокируется, в то время как в главном узле или автономной базе оно выполняется штатно.Рассмотрим рабочие способы исправления ситуации и создания недостающих элементов.
Если готовые сервисные обработки не позволяют создать элемент справочника, создадим его программно. Для этого напишем код внешней обработки или выполним команду в консоли кода.
Обратите внимание на иерархию справочника. Например, в справочнике НаборыДополнительныхРеквизитовИСведений многие предопределенные наборы являются группами. Если в метаданных объект объявлен группой, вызов стандартного метода создания элемента приведет к ошибке.
Посмотрим на пример создания предопределенного элемента:
Объект = Справочники.НаборыДополнительныхРеквизитовИСведений.СоздатьЭлемент();
Объект.Наименование = "Наименование элемента";
Объект.ИмяПредопределенныхДанных = "ИмяПредопределенногоЭлементаИзМетаданных";
Объект.Записать();
Если в конфигураторе предопределенный объект описан как группа справочника, используем соответствующий метод:
Объект = Справочники.НаборыДополнительныхРеквизитовИСведений.СоздатьГруппу();
Объект.Наименование = "Наименование группы";
Объект.ИмяПредопределенныхДанных = "ИмяПредопределеннойГруппыИзМетаданных";
Объект.Записать();
Важное ограничение: платформе нельзя передать произвольную строку в реквизит ИмяПредопределенныхДанных. Передаваемое значение должно в точности совпадать с именем предопределенного элемента, объявленного в ветке метаданных конфигуратора.
Если элемент с похожим наименованием уже был создан пользователями вручную, создавать дубль не требуется. Достаточно получить ссылку на этот элемент, открыть объект на редактирование и прописать точное имя:
Объект = СсылкаНаОбъект.ПолучитьОбъект();
Объект.ИмяПредопределенныхДанных = "ИмяПредопределенногоЭлементаИзМетаданных";
Объект.Записать();
Проанализируем настройки метаданных в конфигураторе. Если у проблемного справочника в палитре свойств реквизит Обновление предопределенных данных находится в значении Авто, изменим его:
При повторном запуске сеанса платформа принудительно создаст недостающие записи в таблицах базы данных.
Если проблемная база работает как подчиненный узел РИБ, платформа целенаправленно ожидает переноса данных из центрального узла и не генерирует их на месте. В таком случае мы можем временно переопределить поведение на уровне информационной базы с помощью метода глобального контекста:
УстановитьОбновлениеПредопределенныхДанныхИнформационнойБазы(РежимОбновленияПредопределенныхДанныхИнформационнойБазы.ОбновлятьАвтоматически);
Также инициализировать автообновление для всей базы можно при запуске через командную строку с помощью параметра /SetPredefinedDataUpdate -UpdateAutomatically.
В крайнем случае для узлов РИБ применяют временное отключение от главного узла:
// Отключаем признак подчиненного узла
ГлавныйУзел = ПланыОбмена.ГлавныйУзел();
ПланыОбмена.УстановитьГлавныйУзел(Неопределено);
// После обновления конфигурации и инициализации данных восстанавливаем узел обратно
ПланыОбмена.УстановитьГлавныйУзел(ГлавныйУзел);
Если ручное создание затруднено большим количеством отсутствующих записей, воспользуемся переносом объектов из демонстрационной или чистой типовой базы соответствующего релиза.
Разберем последовательность шагов: