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