多个提供商和防火墙发布Symfony2

时间:2017-04-29 22:24:42

标签: symfony security doctrine-orm orm

我正在处理简单的应用程序,它处理两种用户,用户和管理员实体的身份验证。我希望有两个独立的防火墙和提供商,我的security.yml文件看起来像这样,我无法验证用户和管理员的任何帮助吗?

security:
encoders:
    AuthentificationBundle\Entity\user:  
           Algorithm:bcrypt
    AuthentificationBundle\Entity\Admin: 
           Algorithm:bcrypt


role_hierarchy:
    ROLE_USER: [ROLE_USER]
    ROLE_ADMIN: [ROLE_ADMIN,ROLE_USER]
    ROLE_SUPER_ADMIN: [ROLE_SUPER_ADMIN,ROLE_ADMIN,ROLE_USER]


providers:
    users:
        entity:
            class: AuthentificationBundle:user
    administrateur:
        entity:
            class: AuthentificationBundle:Admin

firewalls:
    user_area:
        pattern: ^/login
        #anonymous: ~
        form_login:
            login_path: login
            check_path: login_check
            success_handler:  after_login_redirection

        logout:
            path: logout
            target: login
        provider: users
    admin_area:
        pattern: ^/administration
        #anonymous: ~
        form_login:
            login_path: login_admin
            check_path:  admin_login_check
            success_handler:  after_login_redirection

        logout:
            path: /logout
            target: /administration
        provider: administrateur
access_control:
    - { path: ^/login, roles: IS_AUTHENTICATED_ANONYMOUSLY }
    - { path: ^/administration, roles: ROLE_ADMIN }

1 个答案:

答案 0 :(得分:0)

我的灵感来自FOSUserBundle。

基本上我为提供者提供了一个服务,并将其设置为:

providers:
    admins:
        id: user_provider.admins
    users:
        id: user_provider.users

firewalls:
    dev:
        pattern: ^/(_(profiler|wdt)|css|images|js)/
        security: false
    admin_secured_area:
        host: "%admin_host%"
        pattern: ^/*
        form_login:
            provider: admins
            login_path: /login
            check_path: /login_check
            csrf_token_generator: security.csrf.token_manager
        logout:
            path: /logout
            target: /
        anonymous:    true
    users_secured_area:
        host: "%users_host%"
        pattern: ^/*
        form_login:
            provider: users
            login_path: /login
            check_path: /login_check
            csrf_token_generator: security.csrf.token_manager
        logout:
            path: /logout
            target: /
        anonymous:    true

然后我的提供者类是一个名为user_provider.admins

的服务
<?php

namespace APP\AppBundle\Security;

use ...;


class AdminsProvider extends AbstractUserProvider
{
    /** @var Admins */
    protected $userClass;

    /** @var  Admins */
    protected $repositoryClass;

    /**
     * @inheritdoc
     */
    public function setUserClass()
    {
        $this->userClass = Admins::class;
    }

    /**
     * @return Admins
     */
    public function getUserClass()
    {
        return $this->userClass;
    }

    /**
     * @inheritdoc
     */
    public function setUserRepository()
    {
        $this->repositoryClass = Admins::class;
    }

    /**
     * @return Admins
     */
    public function getUserRepository()
    {
        return Admins::class;
    }

}

抽象用户提供程序以结束示例

<?php

namespace App\AppBundle\Security;

use ...;

abstract class AbstractUserProvider implements UserProviderInterface
{
    /**
     * @var EntityManager
     */
    protected $em;

    /**
     * UserProvider constructor.
     *
     * @param EntityManager $em
     */
    public function __construct(EntityManager $em)
    {
        $this->em = $em;
    }

    /**
     * @return mixed
     */
    abstract protected function setUserRepository();

    /**
     * @return mixed
     */
    abstract protected function getUserRepository();

    /**
     * @return mixed
     */
    abstract protected function setUserClass();

    /**
     * @return mixed
     */
    abstract protected function getUserClass();

    /**
     * {@inheritDoc}
     */
    public function loadUserByUsername($username)
    {
        $oUser = $this->em->getRepository($this->getUserRepository())->findOneByUsername($username);

        if (!$oUser) {
            throw new UsernameNotFoundException(sprintf('Username "%s" does not exist.', $username));
        }

        return $oUser;
    }

    /**
     * {@inheritDoc}
     */
    public function refreshUser(UserInterface $oUser)
    {

        if (!$this->supportsClass(get_class($oUser))) {
            throw new UnsupportedUserException(sprintf('Expected an instance of %s, but got "%s".', get_class($this->getUserClass()), get_class($oUser)));
        }

        if (null === $reloadedUser = $this->em->getRepository($this->getUserRepository())->findOneById($oUser->getId())
        ) {
            throw new UsernameNotFoundException(sprintf('User with ID "%s" could not be reloaded.', $oUser->getId()));
        }

        return $reloadedUser;
    }

    /**
     * {@inheritDoc}
     */
    public function supportsClass($class)
    {
        $userClass = $this->getUserRepository();

        return $userClass === $class || is_subclass_of($class, $userClass);
    }
}