dashboard for org
This commit is contained in:
@@ -0,0 +1,100 @@
|
||||
<?php
|
||||
|
||||
namespace App\Filters;
|
||||
|
||||
use App\Services\AccessService;
|
||||
use CodeIgniter\Filters\FilterInterface;
|
||||
use CodeIgniter\HTTP\RequestInterface;
|
||||
use CodeIgniter\HTTP\ResponseInterface;
|
||||
|
||||
/**
|
||||
* RoleFilter - Фильтр проверки ролей и прав доступа
|
||||
*
|
||||
* Применяется к маршрутам для проверки прав доступа на уровне роутинга.
|
||||
*
|
||||
* Использование в роутах:
|
||||
* $routes->get('/admin/users', 'Users::index', ['filter' => 'role:admin']);
|
||||
* $routes->get('/admin/settings', 'Settings::index', ['filter' => 'role:owner']);
|
||||
*/
|
||||
class RoleFilter implements FilterInterface
|
||||
{
|
||||
/**
|
||||
* Проверка доступа перед выполнением запроса
|
||||
*
|
||||
* @param RequestInterface $request
|
||||
* @param array|null $arguments Аргументы из маршрута (роли, разрешения)
|
||||
* @return ResponseInterface|null
|
||||
*/
|
||||
public function before(RequestInterface $request, $arguments = null)
|
||||
{
|
||||
// Если фильтр вызван без аргументов - пропускаем
|
||||
if ($arguments === null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
$access = AccessService::getInstance();
|
||||
|
||||
// Проверка авторизации в организации
|
||||
if (!$access->isAuthenticated()) {
|
||||
// Если пользователь не авторизован в организации - редирект на выбор организации
|
||||
return redirect()->to('/organizations');
|
||||
}
|
||||
|
||||
// Разбор аргументов
|
||||
// Формат: 'role:admin,manager' или 'permission:manage_users:users'
|
||||
if (is_string($arguments) && str_starts_with($arguments, 'role:')) {
|
||||
$roles = explode(',', substr($arguments, 5));
|
||||
$roles = array_map('trim', $roles);
|
||||
|
||||
if (!$access->isRole($roles)) {
|
||||
return $this->forbiddenResponse();
|
||||
}
|
||||
}
|
||||
|
||||
if (is_string($arguments) && str_starts_with($arguments, 'permission:')) {
|
||||
$parts = explode(':', substr($arguments, 11));
|
||||
if (count($parts) >= 2) {
|
||||
$permission = $parts[0];
|
||||
$resource = $parts[1] ?? '*';
|
||||
|
||||
if (!$access->can($permission, $resource)) {
|
||||
return $this->forbiddenResponse();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Обработка после выполнения запроса
|
||||
*
|
||||
* @param RequestInterface $request
|
||||
* @param ResponseInterface $response
|
||||
* @param array|null $arguments
|
||||
* @return void
|
||||
*/
|
||||
public function after(RequestInterface $request, ResponseInterface $response, $arguments = null)
|
||||
{
|
||||
// Ничего не делаем после
|
||||
}
|
||||
|
||||
/**
|
||||
* Возврат ответа "Доступ запрещён"
|
||||
*
|
||||
* @return ResponseInterface
|
||||
*/
|
||||
private function forbiddenResponse(): ResponseInterface
|
||||
{
|
||||
// Проверяем, AJAX ли это запрос
|
||||
if (service('request')->isAJAX()) {
|
||||
return service('response')
|
||||
->setStatusCode(403)
|
||||
->setJSON(['error' => 'Доступ запрещён']);
|
||||
}
|
||||
|
||||
// Для обычных запросов - редирект с сообщением
|
||||
session()->setFlashdata('error', 'У вас нет прав для выполнения этого действия');
|
||||
return redirect()->to('/');
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user