Книга знаний

1С:Предприятие / v8

v8: Авторизация пользователей при входе в программу

Авторизация пользователей при входе в программу. Рассматривается для 1С версии 8.1.Автор статьи:
Последняя редакция №1 от 26.01.07
URL: http://kb.mista.ru/article.php?id=455

Ключевые слова: Авторизация пользователь вход запуск идентификация запрет


По хорошему при серьезном подходе к автоматизации нужно запрещать неавторизованный вход в программу.
Исключение могут составлять крайне редкие случаи, например, демо-версия конфигурации или конфигурация публичного пользования.

Но как правило, наряду с заведением пользователей в конфигураторе имеет смысл сделать в конфигурации справочник "Пользователи", в котором хранить пользователей, соответствующих пользователям в конфигураторе.
Это дает возможность некоторых вещей, например привязки к пользователю некоторых прав, которыми нельзя управлять с помощью метаданного "Роль", построение системы ограничения прав RLS, привязанной к текущему пользователю, сохранение в справочниках и документах информации об авторах объектов, индивидуальные особенности интерфейса, настроек отчетов, событий и т. д.

В этом выпуске будет рассмотрено, как в конфигурации организовать авторизацию пользователей при входе в программу.
Предполагается, что структура пользователей может быть иерархической и пользователи подчинены распределенным базам.
Кому иерархия и/или распределенные базы не нужны, тот может легко все поправить под свой вариант.

Итак. Для выполнения этой задачи в конфигурации требуется сделать нижеперечисленные настройки.

Добавляем в конфигурацию план обмена "РаспределенныеБазы".

Добавляем в конфигурацию иерархический справочник "Пользователи", подчиненный плану обмена "РаспределенныеБазы".

Добавляем в конфигурацию параметр сеанса "ТекущийПользователь" типа "СправочникСсылка.Пользователи".

Добавляем в конфигурацию параметр сеанса "ТекстСообщенияОбОшибкеПриЗапускеПрограммы" типа "Строка неограниченной длины".

Добавляем в конфигурацию параметр сеанса "ТекущийУзелРаспределеннойБазы" типа "ПланОбменаСсылка.РаспределенныеБазы".

Добавляем в конфигурацию константу "ЗапретитьЗапускПрограммыНовымПользователям" типа "Булево".

В модуль приложения в процедуру ПередНачаломРаботыСистемы() вставляем код
Если ПараметрыСеанса.ТекущийПользователь.Пустая() Тогда
   Предупреждение(ПараметрыСеанса.ТекстСообщенияОбОшибкеПриЗапускеПрограммы, 60);
   Отказ = Истина;
КонецЕсли;

В модуль внешнего соединения в процедуру ПриНачалеРаботыСистемы() вставляем код
Если ПараметрыСеанса.ТекущийПользователь.Пустая() Тогда
   ВызватьИсключение(ПараметрыСеанса.ТекстСообщенияОбОшибкеПриЗапускеПрограммы);
   Отказ = Истина;
КонецЕсли;

В модуль сеанса, в котором фирма "1С" рекомендует устанавливать параметры сеанса, в процедуру УстановкаПараметровСеанса() вставляем код
ПараметрыСеанса.ТекущийУзелРаспределеннойБазы = ПланыОбмена.РаспределенныеБазы.ЭтотУзел();
глУстановитьПараметрСеансаТекущийПользователь();

Туда же (в модуль сеанса) вставляем процедуру глУстановитьПараметрСеансаТекущийПользователь() и функцию глЕстьДействующиеПользователи()
Процедура глУстановитьПараметрСеансаТекущийПользователь()
   
   Если ПустаяСтрока(ИмяПользователя()) Тогда
       ПараметрыСеанса.ТекстСообщенияОбОшибкеПриЗапускеПрограммы =
       "Вход в программу без авторизации невозможен.
       |Заполните список пользователей в конфигураторе.";
   ИначеЕсли СтрДлина(СокрЛП(ИмяПользователя())) > Метаданные.Справочники.Пользователи.ДлинаНаименования Тогда
       
       Если Метаданные.Справочники.Пользователи.ДлинаНаименования = 1 Тогда
           ПараметрыСеанса.ТекстСообщенияОбОшибкеПриЗапускеПрограммы =
           "Имя пользователя не может быть длиннее 1 символа.
           |Сократите имя пользователя в конфигураторе.";
       Иначе
           ПараметрыСеанса.ТекстСообщенияОбОшибкеПриЗапускеПрограммы =
           "Имя пользователя не может быть длиннее " + Метаданные.Справочники.Пользователи.ДлинаНаименования + " символов.
           |Сократите имя пользователя в конфигураторе.";
       КонецЕсли;
       
   Иначе
       
       ТекстЗапроса =
       "ВЫБРАТЬ ПЕРВЫЕ 1
       |    Пользователи.Ссылка КАК Пользователь
       |ИЗ
       |    Справочник.Пользователи КАК Пользователи
       |ГДЕ
       |    (НЕ Пользователи.ПометкаУдаления)
       |    И Пользователи.Владелец = &Владелец
       |    И (НЕ Пользователи.ЭтоГруппа)
       |    И Пользователи.Наименование = &Наименование";
       
       Запрос = Новый Запрос(ТекстЗапроса);
       Запрос.УстановитьПараметр("Владелец", ПараметрыСеанса.ТекущийУзелРаспределеннойБазы);
       Запрос.УстановитьПараметр("Наименование", ИмяПользователя());
       Результат = Запрос.Выполнить();
       
       Если Результат.Пустой() Тогда
           
           Если Константы.ЗапретитьЗапускПрограммыНовымПользователям.Получить()
               И глЕстьДействующиеПользователи() Тогда
               ПараметрыСеанса.ТекстСообщенияОбОшибкеПриЗапускеПрограммы =
               "Автоматическое создание новых записей в справочнике ""Пользователи"" запрещено.
               |Обратитесь к администратору для добавления новой записи.";
           Иначе
               
               Попытка
                   
                   Спр = Справочники.Пользователи.СоздатьЭлемент();
                   Спр.УстановитьНовыйКод();
                   Спр.Владелец = ПараметрыСеанса.ТекущийУзелРаспределеннойБазы;
                   Спр.Наименование = ИмяПользователя();
                   Спр.ПолноеНаименование = ПолноеИмяПользователя();
                   Спр.Записать();
                   
                   ПараметрыСеанса.ТекущийПользователь = Спр.Ссылка;
                   
               Исключение
                   ПараметрыСеанса.ТекстСообщенияОбОшибкеПриЗапускеПрограммы = ОписаниеОшибки();
               КонецПопытки;
               
           КонецЕсли;
           
       Иначе
           
           Выборка = Результат.Выбрать();
           Выборка.Следующий();
           
           ПараметрыСеанса.ТекущийПользователь = Выборка.Пользователь;
           
       КонецЕсли;
       
   КонецЕсли;
   
КонецПроцедуры

Функция глЕстьДействующиеПользователи()
   
   ТекстЗапроса =
   "ВЫБРАТЬ ПЕРВЫЕ 1
   |    Пользователи.Ссылка КАК Пользователь
   |ИЗ
   |    Справочник.Пользователи КАК Пользователи
   |ГДЕ
   |    (НЕ Пользователи.ПометкаУдаления)
   |    И Пользователи.Владелец = &Владелец
   |    И (НЕ Пользователи.ЭтоГруппа)";
   
   Запрос = Новый Запрос(ТекстЗапроса);
   Запрос.УстановитьПараметр("Владелец", ПараметрыСеанса.ТекущийУзелРаспределеннойБазы);
   Результат = Запрос.Выполнить();
   
   Если Результат.Пустой() Тогда
       Возврат Ложь;
   Иначе
       Возврат Истина;
   КонецЕсли;
   
КонецФункции

Собственно все. Теперь программа не запустится, если список пользователей в конфигураторе пустой.

И напоследок немного по логике работы.

Параметр сеанса "ТекущийПользователь" вместо комбинации двух одноименных экспортных переменных "глТекущийПользователь" в модуле приложения и модуле внешнего соединения выбран потому, что к нему можно привяхать RLS, а к глобальной переменной нет.

Параметр сеанса "ТекстСообщенияОбОшибкеПриЗапускеПрограммы" заведен исключительно для того, чтобы определить, что пользователь неавторизован и что-то нужно сказать этот самый текст перед принужительным завершением работы программы.
Если устанавливать параметры сеанса в модуле приложения в процедуре ПередНачаломРаботыСистемы() и в модуле внешнего соединения в процедуре ПриНачалеРаботыСистемы(), то этот объект метаданных совершенно не нужен, но, раз уж фирма "1С" рекомендует устанавливать параметры сеанса в модуле сеанса...

Константа "ЗапретитьЗапускПрограммыНовымПользователям" создана для того, чтобы при необходимости запретить автоматически программно создавать новых пользователей в справочнике "Пользователи". Может пригодиться в принципе кому-нибудь.

В модуле внешнего соединения проверка авторизованности пользователя выполняется в процедуре ПриНачалеРаботыСистемы(), а не в процедуре ПередНачаломРаботыСистемы() потому, что в модуле внешнего соединения нет события ПередНачаломРаботыСистемы().
Именно поэтому отказаться от запуска программы уже нельзя, но... нужно, поэтому вызываем исключение с заданным текстом ошибки.

В процедуре глУстановитьПараметрСеансаТекущийПользователь() производится попытка авторизовать пользователя, в случае неудачи параметр сеанса "ТекущийПользователь" остается неустановленным, зато устанавливается параметр сеанса "ТекстСообщенияОбОшибкеПриЗапускеПрограммы".
Пользователь останется неавторизованным в том случае, если:
- Имя пользователя пустое, то есть список пользователей в конфигураторе пустой;
- Имя пользователя длиннее размерности наименования справочника "Пользователи";
- Пользователя нет в справочнике "Пользователи", при этом запрещено запускать программу новым пользователям и в справочнике "Пользователи" есть хоть один пользователь.
Проверка на наличие хотя бы одного пользователя в справочнике "Пользователи" делается для того, чтобы не получилось ситуации, когда в программе установили константу "ЗапретитьЗапускПрограммыНовымПользователям", удалили всех пользователей в справочнике "Пользователи", закрыли программу и... больше никогда не смогли в нее зайти;
- Пользователя нет в справочнике "Пользователи", при этом разрешено запускать программу новым пользователям или в справочнике "Пользователи" нет ни одного пользователя, но при попытке создать пользователя произошла какая-то ошибка и пользователь не создался.

Да, и еще напоследок. Не забывайте, что модуль сеанса выполняется в привелигированном режиме, а поэтому можно смело закрывать права на справочник "Пользователи" тем пользоватям, кто недостоин столь высоких прав. Я сказал можно? Нужно!

Описание | Рубрикатор | Поиск | ТелепатБот | Захваченные статьи | Установки | Форум
© Станислав Митичкин (Волшебник), 2005-2025 | Mista.ru

Яндекс.Метрика