src/Security/FinancialScopeVoter.php line 11

Open in your IDE?
  1. <?php
  2. namespace App\Security;
  3. use App\Entity\FinancialScope;
  4. use App\Service\ScopeResolverService;
  5. use App\Service\HierarchyChecker;
  6. use App\Repository\FinancialScopeRepository;
  7. use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
  8. use Symfony\Component\Security\Core\Authorization\Voter\Voter;
  9. class FinancialScopeVoter extends Voter
  10. {
  11. public const MANAGE = 'FIN_MANAGE';
  12. private $scopeResolver;
  13. private $scopeRepo;
  14. private $hierarchyChecker;
  15. public function __construct(ScopeResolverService $scopeResolver, FinancialScopeRepository $scopeRepo, HierarchyChecker $hierarchyChecker)
  16. {
  17. $this->scopeResolver = $scopeResolver;
  18. $this->scopeRepo = $scopeRepo;
  19. $this->hierarchyChecker = $hierarchyChecker;
  20. }
  21. protected function supports(string $attribute, $subject): bool
  22. {
  23. if ($attribute !== self::MANAGE) return false;
  24. // support any object we can resolve
  25. return true;
  26. }
  27. protected function voteOnAttribute(string $attribute, $subject, TokenInterface $token): bool
  28. {
  29. $user = $token->getUser();
  30. if (!$user || !is_object($user)) return false;
  31. // quick role check: must have ROLE_FINANCIAL or higher
  32. if (!in_array('ROLE_FINANCIAL', $user->getRoles()) && !in_array('ROLE_ADMIN', $user->getRoles())) {
  33. return false;
  34. }
  35. // get user's scopes
  36. $scopes = $this->scopeRepo->findBy(['financialManager' => $user]);
  37. // resolve target
  38. $targetScope = $this->scopeResolver->resolve($subject);
  39. return $this->hierarchyChecker->isCovered($scopes, $targetScope);
  40. }
  41. }