<?php
namespace App\Security;
use App\Entity\Menu;
use App\Entity\Permission;
use App\Entity\Profile;
use App\Entity\User;
use Doctrine\ORM\EntityManagerInterface;
use Sogec\BOBundle\Routing\CRUDAction;
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
use Symfony\Component\Security\Core\Authorization\Voter\Voter;
/**
* Class EntityVoter.
*/
class EntityVoter extends Voter
{
/**
* @var EntityManagerInterface
*/
private $manager;
/**
* EntityVoter constructor.
*
* @param EntityManagerInterface $manager Entity manager.
*/
public function __construct(EntityManagerInterface $manager)
{
$this->manager = $manager;
}
/**
* {@inheritdoc}
*/
protected function supports($action, $route)
{
// if the attribute isn't one we support, return false
if (!in_array($action, array(CRUDAction::SHOW, CRUDAction::EDIT, CRUDAction::DELETE, CRUDAction::NEW))) {
return false;
}
return true;
}
/**
* @param string $action
* @param mixed $route
* @param TokenInterface $token
*
* @return bool
*/
protected function voteOnAttribute($action, $route, TokenInterface $token)
{
$user = $token->getUser();
if (!$user instanceof User) {
// the user must be logged in; if not, deny access
return false;
}
return $this->canActionByProfile($user, $route, $action);
}
/**
* @param User $user
* @param string $route
* @param string $action
*
* @return bool
*/
private function canActionByProfile(User $user, $route, $action)
{
$profile = $user->getProfile();
$permission = $this->getPermissionByOption($profile, $route);
if (!$permission) {
return false;
}
if ('ROLE_SUPER_ADMIN' === $user->getRoles()[0]) {
return true;
}
return 1 === (int) $permission->getActions()[$action] ? true : false;
}
/**
* @param Profile $profile
* @param string $route
*
* @return Permission|bool|null|object
*/
private function getPermissionByOption(Profile $profile, $route)
{
$menu = $this->manager->getRepository(Menu::class)
->findOneBy(['route' => $route]);
$permission = $this->manager->getRepository(Permission::class)
->findOneBy(['menu' => $menu, 'profile' => $profile]);
return $permission ? $permission : false;
}
}