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