Skip to content

Commit 68da041

Browse files
committed
Update voter section of best practices
1 parent 3ebf2d0 commit 68da041

File tree

1 file changed

+45
-15
lines changed

1 file changed

+45
-15
lines changed

best_practices/security.rst

Lines changed: 45 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -264,37 +264,66 @@ the same ``getAuthorEmail`` logic you used above:
264264
265265
namespace AppBundle\Security;
266266
267-
use Symfony\Component\Security\Core\Authorization\Voter\AbstractVoter;
267+
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
268+
use Symfony\Component\Security\Core\Authorization\AccessDecisionManagerInterface;
269+
use Symfony\Component\Security\Core\Authorization\Voter\Voter;
268270
use Symfony\Component\Security\Core\User\UserInterface;
271+
use AppBundle\Entity\Post;
269272
270-
// AbstractVoter class requires Symfony 2.6 or higher version
271-
class PostVoter extends AbstractVoter
273+
// Voter class requires Symfony 2.8 or higher version
274+
class PostVoter extends Voter
272275
{
273276
const CREATE = 'create';
274277
const EDIT = 'edit';
275278
276-
protected function getSupportedAttributes()
279+
/**
280+
* @var AccessDecisionManagerInterface
281+
*/
282+
private $decisionManager;
283+
284+
public function __construct(AccessDecisionManagerInterface $decisionManager)
277285
{
278-
return array(self::CREATE, self::EDIT);
286+
$this->decisionManager = $decisionManager;
279287
}
280288
281-
protected function getSupportedClasses()
289+
protected function supports($attribute, $subject)
282290
{
283-
return array('AppBundle\Entity\Post');
291+
if (!in_array($attribute, array(self::CREATE, self::EDIT))) {
292+
return false;
293+
}
294+
295+
if (!$subject instanceof Post) {
296+
return false;
297+
}
298+
299+
return true;
284300
}
285301
286-
protected function isGranted($attribute, $post, $user = null)
302+
protected function voteOnAttribute($attribute, $subject, TokenInterface $token)
287303
{
304+
$user = $token->getUser();
305+
/** @var Post */
306+
$post = $subject; // $subject must be a Post instance, thanks to the supports method
307+
288308
if (!$user instanceof UserInterface) {
289309
return false;
290310
}
291311
292-
if ($attribute === self::CREATE && in_array('ROLE_ADMIN', $user->getRoles(), true)) {
293-
return true;
294-
}
295-
296-
if ($attribute === self::EDIT && $user->getEmail() === $post->getAuthorEmail()) {
297-
return true;
312+
switch ($attribute) {
313+
case self::CREATE:
314+
// if the user is an admin, allow them to create new posts
315+
if ($this->decisionManager->decide($token, array('ROLE_ADMIN'))) {
316+
return true;
317+
}
318+
319+
break;
320+
case self::EDIT:
321+
// if the user is the author of the post, allow them to edit the posts
322+
if ($user->getEmail() === $post->getAuthorEmail()) {
323+
return true;
324+
}
325+
326+
break;
298327
}
299328
300329
return false;
@@ -310,6 +339,7 @@ To enable the security voter in the application, define a new service:
310339
# ...
311340
post_voter:
312341
class: AppBundle\Security\PostVoter
342+
arguments: ['@security.access.decision_manager']
313343
public: false
314344
tags:
315345
- { name: security.voter }
@@ -337,7 +367,7 @@ via the even easier shortcut in a controller:
337367
*/
338368
public function editAction($id)
339369
{
340-
$post = // query for the post ...
370+
$post = ...; // query for the post
341371
342372
$this->denyAccessUnlessGranted('edit', $post);
343373

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy