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