src/Manager/User/PermissionManager.php line 44

Open in your IDE?
  1. <?php
  2. namespace App\Manager\User;
  3. use App\Annotations\HasPermission;
  4. use App\Annotations\PermissionKey;
  5. use App\Entity\Menu;
  6. use App\Entity\User\User;
  7. use Doctrine\Common\Annotations\Reader;
  8. use Doctrine\ORM\EntityManagerInterface;
  9. use Symfony\Component\Routing\Annotation\Route;
  10. use Symfony\Component\Routing\RouterInterface;
  11. use Symfony\Component\Security\Core\Security;
  12. class PermissionManager
  13. {
  14.     private Security $security;
  15.     private Reader $annotationReader;
  16.     private RouterInterface $router;
  17.     private EntityManagerInterface $entityManager;
  18.     public function __construct(Security $securityReader $annotationReaderRouterInterface $router,
  19.                                 EntityManagerInterface $entityManager)
  20.     {
  21.         $this->security $security;
  22.         $this->annotationReader $annotationReader;
  23.         $this->router $router;
  24.         $this->entityManager $entityManager;
  25.     }
  26.     public function hasPermission(string $action null, ?\ReflectionMethod $method null, ?Menu $menu null): bool
  27.     {
  28.         if ($method)
  29.         {
  30.             return $this->hasPermissionByMethod($method);
  31.         }
  32.         elseif ($menu)
  33.         {
  34.             return $this->hasPermissionByMenu($action$menu);
  35.         }
  36.         return false;
  37.     }
  38.     public function hasPermissionByRoute(string $route): bool
  39.     {
  40.         try {
  41.             if ($this->router->getRouteCollection()->get($route) === null)
  42.             {
  43.                 throw new \Exception(`The controller for route "${$route}" does not exist`);
  44.             }
  45.             return $this->hasPermissionByMethod(
  46.                 new \ReflectionMethod($this->router->getRouteCollection()->get($route)->getDefault('_controller'))
  47.             );
  48.         } catch (\ReflectionException $e) {
  49.             return true;
  50.         }
  51.     }
  52.     private function getMenuByRouteName(string $routeName)
  53.     {
  54.         return $this->entityManager->getRepository(Menu::class)->findOneBy([
  55.             'route' => $routeName
  56.         ]);
  57.     }
  58.     private function hasPermissionByMethod(\ReflectionMethod $method): bool
  59.     {
  60.         /** @var PermissionKey $permissionKey */
  61.         $permissionKey $this->annotationReader->getClassAnnotation($method->getDeclaringClass(), PermissionKey::class);
  62.         /** @var HasPermission $needlePermission */
  63.         $needlePermission $this->annotationReader->getMethodAnnotation($methodHasPermission::class);
  64.         if (!$permissionKey || !$needlePermission) {
  65.             // If the controller OR the action are not defined, access is granted
  66.             return true;
  67.         }
  68.         $menu $this->entityManager->getRepository(Menu::class)->findOneBy(['route' => $this->annotationReader->getMethodAnnotation($methodRoute::class)->getName()]);
  69.         if (!$menu) {
  70.             $menu $this->entityManager->getRepository(Menu::class)->findOneBy(['permission_key' => $permissionKey->name]);
  71.         }
  72.         return $this->hasPermissionByMenu($needlePermission->action$menu);
  73.     }
  74.     public function hasPermissionByMenu(string $actionMenu $menu): bool
  75.     {
  76.         $user $this->security->getUser();
  77.         if (!$user instanceof User) {
  78.             return false;
  79.         }
  80.         $menuPermissions = !$menu->getPermissions()->isEmpty() ? $menu $menu->getMenu() ?? $menu;
  81.         return (bool) $menuPermissions->getPermissions()->filter(
  82.             fn ($v) => $v->getProfile() === $user->getProfile()
  83.         )->first()->getActions()[$action];
  84.     }
  85. }