В процессе разработки и тестирования часто возникает ситуация, когда пользователям в рабочих базах права администратора запрещены, но в тестовых копиях эти права им необходимы для полноценной проверки функционала, отладки или исправления данных. Настраивать права вручную в каждой новой копии трудозатратно. Рассмотрим, как автоматизировать этот процесс, чтобы пользователь мог самостоятельно или автоматически получить необходимые роли «из-под своей учетной записи», используя технические возможности платформы 1С:Предприятие.
Первое, что приходит на ум программисту — использовать метод УстановитьПривилегированныйРежим(Истина). Однако важно понимать специфику работы платформы с системными таблицами. Привилегированный режим отключает проверку прав на уровне объектов базы данных (справочники, документы, регистры), но он не всегда позволяет изменять состав ролей пользователя информационной базы (ИБ), если у текущего сеанса отсутствует право Администрирование. Платформа защищает список пользователей на более глубоком уровне.
Выясним причину: объект ПользовательИнформационнойБазы относится к системным механизмам. Если код запускается во внешней обработке, платформа блокирует доступ к изменению прав, так как это создало бы критическую уязвимость. Поэтому нам потребуются более изощренные методы, реализуемые на стороне сервера или через специализированные параметры запуска.
Рассмотрим вариант, при котором мы создаем в системе «служебного» пользователя с правами администратора. Этот пользователь не должен отображаться в списке выбора при запуске базы, а его пароль должен быть скрыт от обычных сотрудников.
Алгоритм действий следующий:
/C идентификатор текущего пользователя и выполняет код назначения прав.Разберем пример кода в модуле приложения (событие ПередНачаломРаботыСистемы):
Процедура ПередНачаломРаботыСистемы(Отказ)
Параметр = ПараметрЗапуска;
// Проверяем, что в параметре передан ожидаемый ключ (например, GUID пользователя)
Если Лев(Параметр, 10) = "SetAdminTo" Тогда
ИмяПользователяДляПрав = Сред(Параметр, 12);
НазначитьПраваАдминистратораПрограммно(ИмяПользователяДляПрав);
// Завершаем работу служебного сеанса после выполнения задачи
ЗавершитьРаботуСистемы(Ложь);
КонецЕсли;
КонецПроцедуры
Для реализации самой функции назначения прав используем общий модуль с установленным флагом Привилегированный и Сервер. Проанализируем пример функции:
Процедура НазначитьПраваАдминистратораПрограммно(ИмяПользователя) Экспорт
УстановитьПривилегированныйРежим(Истина);
ПользовательИБ = ПользователиИнформационнойБазы.НайтиПоИмени(ИмяПользователя);
Если ПользовательИБ <> Неопределено Тогда
// Находим роль "ПолныеПрава" или "Администратор"
РольАдмин = Метаданные.Роли.ПолныеПрава;
Если Не ПользовательИБ.Роли.Содержит(РольАдмин) Тогда
ПользовательИБ.Роли.Добавить(РольАдмин);
ПользовательИБ.Записать();
ЗаписьЖурналаРегистрации("ПраваДоступа", УровеньЖурналаРегистрации.Информационный, , ,
"Пользователю " + ИмяПользователя + " назначены права администратора.");
КонецЕсли;
КонецЕсли;
КонецПроцедуры
Важный нюанс безопасности: Чтобы пароль служебного пользователя не «светился» в коде, можно исключить текст общего модуля из поставки или использовать механизмы расширений, которые подключаются только в тестовых базах.
Этот способ является наиболее «чистым» и безопасным. Мы создаем регламентное задание, которое будет запускаться только в том случае, если база определена как копия. Регламентные задания на сервере всегда выполняются с высокими привилегиями, что позволяет им беспрепятственно управлять списком пользователей.
Проанализируем ситуацию: как системе понять, что она находится в тестовом контуре? Начиная с версии платформы 8.3.3, 1С умеет определять перемещение базы. Мы можем использовать стандартные механизмы БСП (Библиотеки стандартных подсистем) для проверки признака копии.
Рассмотрим пример кода для регламентного задания:
Процедура ВыдатьПраваВТестовойБазе() Экспорт
// Проверяем, является ли текущая база копией
Инфо = СоединенияИИнформационнаяБаза.ПолучитьПараметрыИнформационнойБазы();
Если Не Инфо.КопияИБ Тогда
Возврат; // В рабочей базе ничего не делаем!
КонецЕсли;
// Получаем список пользователей, которым разрешено администрирование в тестах
СписокЮзеров = ПолучитьСписокПривилегированныхСотрудников();
Для Каждого ИмяПользователя Из СписокЮзеров Цикл
НазначитьПраваАдминистратораПрограммно(ИмяПользователя);
КонецЦикла;
КонецПроцедуры
Этот метод хорош тем, что он не требует от пользователя никаких дополнительных действий. Как только база восстанавливается из бэкапа в тестовый контур, регламентное задание по расписанию (или при первом запуске) актуализирует права нужных сотрудников.
Если процесс создания тестовых баз автоматизирован (например, через SQL-бэкапы и скрипты PowerShell), можно добавить финальный шаг в скрипт развертывания. Скрипт может запустить конфигуратор 1С в пакетном режиме и выполнить внешнюю обработку, которая назначит права.
Пример командной строки для запуска пакетного задания:
"C:\Program Files\1cv8\common\1cestart.exe" DESIGNER /F "ПутьКБазе" /N "Admin" /P "Pass" /Execute "C:\Scripts\SetAdminRights.epf" /Batch "C:\Scripts\log.txt"
В самой обработке SetAdminRights.epf в процедуре ПриОткрытии (или ПередЗаписью) должен содержаться код по работе с ПользователиИнформационнойБазы, аналогичный приведенному выше, после чего выполнение должно завершаться командой ЗавершитьРаботуСистемы().
При реализации любого из этих методов необходимо строго соблюдать следующие правила:
СтрокаСоединенияИнформационнойБазы() для сверки с эталоном.ЖурналРегистрации все случаи программного изменения прав. Это поможет в будущем понять, кто и когда получил доступ.GUID пользователей, которым разрешено повышение прав в тестовой среде.ГруппыДоступа. В этом случае вам нужно программно добавлять пользователя в группу доступа «Администраторы» через программный интерфейс (API) БСП, иначе система может сбросить права при ближайшем обновлении или синхронизации.Рассмотрим, как выглядит добавление в группу доступа через БСП:
// Пример для конфигураций на базе БСП
ГруппаАдмины = Справочники.ГруппыДоступа.НайтиПоНаименованию("Администраторы");
Если Не ГруппаАдмины.Пустая() Тогда
ОбъектГруппы = ГруппаАдмины.ПолучитьОбъект();
// Проверяем, есть ли уже пользователь в табличной части
СтрокаПользователя = ОбъектГруппы.Пользователи.Найти(НужныйПользовательСсылка, "Пользователь");
Если СтрокаПользователя = Неопределено Тогда
НоваяСтрока = ОбъектГруппы.Пользователи.Добавить();
НоваяСтрока.Пользователь = НужныйПользовательСсылка;
ОбъектГруппы.Записать();
КонецЕсли;
КонецЕсли;
Таким образом, комбинируя использование привилегированных модулей, параметров запуска и проверки контекста базы (копия/оригинал), можно создать удобный и безопасный механизм самообслуживания для разработчиков и тестировщиков, не компрометируя безопасность основной рабочей базы.