Перейти к содержимому

Пользователи, группы и права доступа в 1С-Битрикс

Учётные записи, группы и права - механика, на которой держится разграничение доступа и в публичной части, и в админке.

Как это работает

Пользователь в платформе один на всё: и на сайт, и на панель управления. Различает их не тип записи, а права группы. Человек может годами работать на сайте и ни разу не попасть в админку просто потому, что доступ туда - отдельное право, которого у его группы нет.

Права выдаются группам. Пользователь входит в одну или несколько, права складываются, и побеждает наибольшее из них. Ограничить доступ, добавив человека в «урезанную» группу, невозможно: итог определяет самая разрешающая группа.

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

Две группы существуют всегда. Первая - администраторы, у неё полный доступ мимо любых проверок. Вторая - все пользователи, включая неавторизованных, и именно через неё раздаются права гостю. Удалить их нельзя, а вот случайно выдать группе гостей лишнее - обычное дело.

Примеры

Читаем текущего пользователя средствами ядра D7:

use Bitrix\Main\Engine\CurrentUser;
$user = CurrentUser::get();
printf("id=%s авторизован=%s админ=%s\n",
$user->getId() ?: '-',
$user->isAuthorized() ? 'да' : 'нет',
$user->isAdmin() ? 'да' : 'нет');

Объект текущего пользователя доступен и в публичной части, и в админке, и в контроллерах. Глобальный $USER делает то же самое, но остаётся объектом старого ядра.

Проверяем права перед действием, а не после:

global $USER;
if (!$USER->CanDoOperation('edit_php')) {
throw new RuntimeException('недостаточно прав');
}

Проверка по названию операции надёжнее проверки на администратора: она переживает появление новых ролей и не требует правки кода при смене состава групп.

Создаём пользователя и кладём его в группы:

$user = new CUser();
$id = $user->Add([
'LOGIN' => 'manager01',
'EMAIL' => 'manager01@example.com',
'PASSWORD' => $password,
'CONFIRM_PASSWORD' => $password,
'GROUP_ID' => [5, 6], // группы задаются при создании или отдельным вызовом
'ACTIVE' => 'Y',
]);
if (!$id) {
echo $user->LAST_ERROR; // текст ошибки лежит в свойстве, а не возвращается
}

Метод возвращает идентификатор или false, а причина отказа лежит в свойстве объекта. Пароль и подтверждение обязаны совпадать, иначе запись не создастся.

Ловим событие авторизации:

/local/php_interface/init.php
Bitrix\Main\EventManager::getInstance()->addEventHandler(
'main', 'OnAfterUserLogin',
static function (&$fields) {
// сюда попадаем после успешного входа: журнал, метка времени, своя логика
}
);

Событие приходит уже после проверки пароля и прав. Отменить вход из него нельзя - для этого есть событие до авторизации.

Справочник API

Что нужноМетод
Текущий пользователь в D7Bitrix\Main\Engine\CurrentUser::get()
Проверить операцию$USER->CanDoOperation('код_операции')
Группы пользователя$USER->GetUserGroupArray()
Создать пользователяCUser::Add(array $fields)
Сменить группыCUser::SetUserGroup($id, array $groups)
Права на файл или раздел$APPLICATION->GetFileAccessPermission($path)

Частые ошибки

Проверка на администратора вместо проверки операции. Код с isAdmin() работает до появления первой роли между гостем и администратором, после чего его приходится переписывать целиком.

Выдача прав человеку вместо группы. Через год никто не помнит, почему у этого пользователя доступ шире, чем у коллег с той же должностью.

Забытая группа «все пользователи». Права, выданные ей, получает и неавторизованный посетитель, и это самая частая причина утечки закрытых разделов в поиск.

Частые вопросы

Чем CurrentUser отличается от глобального $USER?

CurrentUser - объект нового ядра с типизированными методами, $USER - объект старого. Оба описывают одного и того же пользователя, но в новом коде берут первый: он доступен в контроллерах и не требует global.

Можно ли запретить что-то отдельному пользователю?

Штатно нет: права складываются из групп, и запрещающих прав в платформе не существует. Ограничение делают, убрав человека из разрешающей группы, а не добавив в запрещающую.

Как узнать, почему пользователь не видит раздел?

Смотрят права на раздел структуры и права его групп на нужный модуль. Эти два уровня независимы, и отказ приходит от того из них, который строже, без указания, от какого именно.

Что происходит с правами гостя?

Гость числится в группе «все пользователи» и получает её права. Именно поэтому эту группу не наделяют доступом ни к чему, кроме публичного содержимого.

Связанные темы

Первоисточники