src/Security/Voter/RequestDuplication/CategoryCanBeDuplicated.php line 13

Open in your IDE?
  1. <?php
  2. namespace App\Security\Voter\RequestDuplication;
  3. use App\Helper\UserRequest\MdmProviderInterface;
  4. use App\Manager\UserRequestManager;
  5. use Psr\Log\LoggerInterface;
  6. use Symfony\Component\PropertyAccess\PropertyAccess;
  7. use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
  8. use Symfony\Component\Security\Core\Authorization\Voter\Voter;
  9. use WebServiceCollectionBundle\Model\AtlasPce\UserRequestRequestModel;
  10. class CategoryCanBeDuplicated extends Voter
  11. {
  12.     public const REQUEST_DUPLICATION_ATTR 'REQUEST_DUPLICATION';
  13.     /**
  14.      * @var LoggerInterface
  15.      */
  16.     protected $logger;
  17.     /**
  18.      * @var MdmProviderInterface
  19.      */
  20.     protected $mdmProvider;
  21.     /**
  22.      * @param LoggerInterface $logger
  23.      * @param MdmProviderInterface $mdmProvider
  24.      */
  25.     public function __construct(
  26.         LoggerInterface $logger,
  27.         MdmProviderInterface $mdmProvider
  28.     ) {
  29.         $this->logger      $logger;
  30.         $this->mdmProvider $mdmProvider;
  31.     }
  32.     /**
  33.      * {@inheritdoc}
  34.      */
  35.     public function supports($attribute$subject)
  36.     {
  37.         $isAttributeCopyCheck = static::REQUEST_DUPLICATION_ATTR === $attribute;
  38.         $isRequestValidObject = !is_null($subject) && (get_class($subject) === UserRequestRequestModel::class);
  39.         return $isAttributeCopyCheck && $isRequestValidObject;
  40.     }
  41.     /**
  42.      * {@inheritdoc}
  43.      */
  44.     public function voteOnAttribute($attribute$subjectTokenInterface $token)
  45.     {
  46.         $accessor   PropertyAccess::createPropertyAccessor();
  47.         $data       $subject->getData();
  48.         $categoryId $accessor->getValue($data'[requestCategory][id]');
  49.         $this->logger->info('[COPY CATEGORY] trying to duplicate request with category {categoryId}', [
  50.             'categoryId' => $categoryId,
  51.         ]);
  52.         // In case category hasn't been set already
  53.         if (!$categoryId) {
  54.             return true;
  55.         }
  56.         $user $token->getUser();
  57.         $userRoles $user->getRoles();
  58.         // if we take only categories, roles are lost.
  59.         $categories $this->mdmProvider->getAll(UserRequestManager::PCE_REQUEST_TYPE)['categories'];
  60.         $this->logger->info('[COPY CATEGORY] User roles {userRoles}', [
  61.             'userRoles' => json_encode($userRoles),
  62.         ]);
  63.         // Keep categories that either have no role restrictions or those what that user has ALL roles required by the category
  64.         $categories array_filter($categories, function(array $category) use ($userRoles) {
  65.             if (empty($category['roles'])) {
  66.                 $this->logger->info('[COPY CATEGORY] Category {categoryLabel} does not require any roles, it may be duplicated by anyone', [
  67.                     'categoryLabel' => $category['label'],
  68.                 ]);
  69.                 return true;
  70.             }
  71.             $this->logger->info('[COPY CATEGORY] Category {categoryLabel} requires roles {roles}', [
  72.                 'categoryLabel' => $category['label'],
  73.                 'roles' => json_encode($category['roles']),
  74.             ]);
  75.             return array_reduce($category['roles'], function($carry$roleInCategory) use ($userRoles) {
  76.                 return $carry && in_array($roleInCategory$userRoles);
  77.             }, true);
  78.         });
  79.         $this->logger->info('[COPY CATEGORY] Categories the user may copy {categories}', [
  80.             'categories' => json_encode($categories),
  81.         ]);
  82.         // Key = category id
  83.         $categoriesIds array_keys($categories);
  84.         $this->logger->info('[COPY CATEGORY] Request category incuded? {theAnswer}', [
  85.             'theAnswer' => in_array($categoryId$categoriesIds),
  86.         ]);
  87.         // Check if user has access to category
  88.         return in_array($categoryId$categoriesIds);
  89.     }
  90. }