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