0

I have written an RBAC (Role-based access control) implementation within my Symfony project a few days ago using Symfony Voters.

This is my universal voter for checking if the member has the ability to, for example, create on a specific endpoint:

class AbilityVoter extends Voter
{
public function __construct(MemberRepositoryInterface $memberRepository)
{
    $this-memberRepository = $memberRepository;
}

protected function supports(
    string $attribute,
    $subject
): bool {
    if (!in_array($attribute, ['create'])) {
        return false;
    }
    return true;
}

protected function voteOnAttribute(
    string $attribute,
    $subject,
    TokenInterface $token
): bool {

    $user = $token->getUser();
    if (!$user instanceof UserInterface) {
        return false;
    }

    /** @var Member $member */
    $member = $user;

    return $this->memberRepository->hasAbility(
        $member->getId(),
        $attribute,
        $subject
    );
  }
}   

There is a part I don’t think I've addressed though: how do I hook into that within command handlers or other such places in my code?

On some example endpoints, that means that restricting access to certain endpoints is not enough and there will need to be RBAC-aware logic somewhere in the endpoint that determines whether the request is allowable.

For example, if the member is not allowed to post content for others but the request contains someone else’s member ID, it should be denied, otherwise, it should be allowed.

Can someone suggest the best way to do this and implement proof-of-concept code for the example above? Should I create some custom voters (that extend my base class) and use that? Or do we need to inject a service into the command handler so that it makes that decision?

Can someone help with that? What would be the beast approach in this case? Thanks

jabepa
  • 61
  • 5

0 Answers0