src/Security/ContactVoter.php line 10

Open in your IDE?
  1. <?php
  2. // src/Security/PostVoter.php
  3. namespace App\Security;
  4. use App\Entity\Contact;
  5. use App\Entity\User;
  6. use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
  7. use Symfony\Component\Security\Core\Authorization\Voter\Voter;
  8. class ContactVoter extends Voter
  9. {
  10. // these strings are just invented: you can use anything
  11. const VIEW = 'view';
  12. const EDIT = 'edit';
  13. protected function supports(string $attribute, $subject): bool
  14. {
  15. // if the attribute isn't one we support, return false
  16. if (!in_array($attribute, [self::VIEW, self::EDIT])) {
  17. return false;
  18. }
  19. // only vote on `Post` objects
  20. if (!$subject instanceof Contact) {
  21. return false;
  22. }
  23. return true;
  24. }
  25. protected function voteOnAttribute(string $attribute, $subject, TokenInterface $token): bool
  26. {
  27. $user = $token->getUser();
  28. if (!$user instanceof User) {
  29. // the user must be logged in; if not, deny access
  30. return false;
  31. }
  32. // you know $subject is a Post object, thanks to `supports()`
  33. /** @var Post $post */
  34. $contact = $subject;
  35. switch ($attribute) {
  36. case self::VIEW:
  37. return $this->canView($contact, $user);
  38. case self::EDIT:
  39. return $this->canEdit($contact, $user);
  40. }
  41. throw new \LogicException('This code should not be reached!');
  42. }
  43. private function canView(Contact $contact, User $user): bool
  44. {
  45. // if they can edit, they can view
  46. if ($this->canEdit($contact, $user)) {
  47. return true;
  48. }
  49. return ($contact == $user->getContact() || $contact->getParent() == $user->getContact());
  50. }
  51. private function canEdit(Contact $contact, User $user): bool
  52. {
  53. // this assumes that the Post object has a `getOwner()` method
  54. return ($contact == $user->getContact() || $contact->getParent() == $user->getContact());
  55. }
  56. }