Symfony2检查服务中的用户角色

时间:2015-07-04 14:02:09

标签: symfony

如何在symfony2服务的代码中检查用户角色?我应该只是将用户角色对象发送到服务,还是有解决方案允许我从服务级别进行检查?

5 个答案:

答案 0 :(得分:12)

其他答案是您传递容器而不是授权检查程序。虽然它们工作,但它们对容器产生了严格的依赖性,使得将代码迁移到其他项目变得更加困难。相反,您应该只通过授权检查程序。

以下是symfony docs

中的示例

应用程序/配置/ services.yml

services:
    newsletter_manager:
        class:     "AppBundle\Newsletter\NewsletterManager"
        arguments: ["@security.authorization_checker"]

的src /的appbundle /新闻/ NewsletterManager.php

namespace AppBundle\Newsletter;

use Symfony\Component\Security\Core\Authorization\AuthorizationCheckerInterface;
use Symfony\Component\Security\Core\Exception\AccessDeniedException;
// ...

class NewsletterManager
{
    protected $authorizationChecker;

    public function __construct(AuthorizationCheckerInterface $authorizationChecker)
    {
        $this->authorizationChecker = $authorizationChecker;
    }

    public function sendNewsletter()
    {
        if (false === $this->authorizationChecker->isGranted('ROLE_NEWSLETTER_ADMIN')) {
            throw new AccessDeniedException();
        }

        // ...
    }

    // ...
}

答案 1 :(得分:2)

假设:

  • 您在服务中注入<?php use Luracast\Restler\Scope; use Luracast\Restler\Restler; use Kiosk\Main; use Kiosk\Drone\Drone; require_once __DIR__.'/vendor/autoload.php'; $file = __DIR__ . "/config.json"; $main = new Main($file); $c = $main->c; Scope::register('Kiosk\\Drone\\Drone', function () use ($c) { return new DataTable($c->get('config'), $c->get('logger')); }); $r = new Restler(); $r->addAPIClass('Luracast\\Restler\\Resources'); $r->addAPIClass('Kiosk\\Drone\\Drone','drone'); $r->addAuthenticationClass('Kiosk\\System\\TokenAuth'); $r->handle(); ?>

    public function __construct(SecurityContext $ securityContext){     $ this-&gt; securityContext = $ securityContext; }

  • 您正在使用FosUserBundle

  • 我理解你的问题:-)

你应该能够做到:

security.context

更新2016/11/28

  1. 更新答案以传递特定的依赖项而不是整个容器,因为这是一种不好的做法(请参阅@Shady的评论)
  2. 请注意,从Symfony 2.6开始, SecurityContext 已弃用,您应该使用 TokenStorage

答案 2 :(得分:0)

编辑@Mick - 不要做以下

有关详细信息,请参阅here

我认为如果在User实体中实现isGranted函数会更容易:

Class User implements UserInterface {
    ...
    public function isGranted($role)
    {
        return in_array($role, $this->getRoles());
    }
}

现在,您可以轻松地在应用程序的每个层中检查授予的角色。在PHP中:

$user->isGranted("USER_ADMIN")

或者在Twig:

user.granted("USER_ADMIN")

如果您需要检查当前用户的角色,可以在Twig中执行此操作:

app.user.granted("USER_ADMIN")

注意:变量&#34; app&#34;是全球定义的。

注意2:如果您在应用的安全区域之外使用此代码,则此代码可能会抛出异常,因为app.user将为NULL。

答案 3 :(得分:0)

答案是,为了能够在服务中使用Symfony2类,您需要使用容器提供服务。

服务定义:

services:
  /.../:
    class: /.../
    arguments: ['@service_container']

服务档案:

使用Symfony \ Component \ DependencyInjection \ ContainerInterface作为Container;

class globalHelper {    

    private $container;

    public function __construct(Container $container) {
        $this->container = $container;
    }

答案 4 :(得分:0)

小心......

在安全问题上要非常小心你正在做的事情。不要做THIS

这是因为,您需要了解TokenInterfaceUserInterface不同。

  

TokenInterface是用户身份验证的接口   信息。

您必须使用它 - 如果您当前的服务中没有令牌,请使用SecurityContextAccessDecisionManager

注意 :在Symfony中&gt; 2.6,已制作了一些improvements,并且已弃用SecurityContext,并将其拆分为TokenStorageAuthorizationChecker。因此,您可以继续使用AuthorizationChecker

看!甚至FOSUserBundle implementation也谈到了它:

/**
 * Never use this to check if this user has access to anything!
 *
 * Use the SecurityContext, or an implementation of AccessDecisionManager
 * instead, e.g.
 *
 *         $securityContext->isGranted('ROLE_USER');
 *
 * @param string $role
 * @return Boolean
 */
function hasRole($role);

了解它的工作原理,例如getRolesHierarchical roles等内容。

数据库中的ROLES不值得信任 - 如果您从数据库中获取User对象,并使用您的getRoles()或者更糟糕的是您创建的特殊isGranted($role),他们将不会您期望用户拥有的角色。

This应该是你的圣经,现在你可以理解它们之间的区别:

1 $user->getRoles()

array(2) { 
    [0]=> string(10) "ROLE_ADMIN" 
    [1]=> string(9) "ROLE_USER" 
}

2 $this->token->getRoles()

array(2) { 
    [0]=> object(Symfony\Component\Security\Core\Role\Role) 
        (1) { ["role":"Symfony\Component\Security\Core\Role\Role":private]=> string(10) "ROLE_ADMIN" } 
    [1]=> object(Symfony\Component\Security\Core\Role\Role)
        (1) { ["role":"Symfony\Component\Security\Core\Role\Role":private]=> string(22) "ROLE_ALLOWED_TO_SWITCH" } 
    [2]=> object(Symfony\Component\Security\Core\Role\Role)
        (1) { ["role":"Symfony\Component\Security\Core\Role\Role":private]=> string(9) "ROLE_USER" } 

} 

3 $this->token->getUser->getRoles()

array(2) { 
    [0]=> string(10) "ROLE_ADMIN" 
    [1]=> string(22) "ROLE_ALLOWED_TO_SWITCH" 
    [2]=> string(9) "ROLE_USER" 
}

当你有 security.yml

security:
    role_hierarchy:
        ROLE_ADMIN: [ROLE_ALLOWED_TO_SWITCH]
相关问题