dousha7645 2016-04-25 08:41
浏览 91
已采纳

对于必须保持向后兼容性的authenticator类的方法

Before Symfony 2.8 SimplePreAuthenticatorInterface was in the following namespace Symfony\Component\Security\Core\Authentication\SimplePreAuthenticatorInterface It have been deprecated in 2.8 and changed in 3.0 to Symfony\Component\Security\Http\Authentication\SimplePreAuthenticatorInterface

now I'm writing a bundle which must work either in symfony 2.7 and symfony 3.0 it is an api authenticator bundle for a private use.

I would like to write a factory for it which checks interface existance

example from FosUserBundle

if (interface_exists('Symfony\Component\Security\Core\Authentication\Token\Storage\TokenStorageInterface')) {
    $tokenStorage = $this->get('security.token_storage');
} else {
    $tokenStorage = $this->get('security.context');
}

but my class which implements this interface is a service in DI and symfony firewall directly uses this.

My question is how could I make this abstraction in a manner of best practise and logical.

AccessTokenAuthenticator Class :

<?php

namespace MyCompany\SBundle\Security;
// this usage for before symfony 2.8
use Symfony\Component\Security\Core\Authentication\SimplePreAuthenticatorInterface;

/**
 * Class AccessTokenAuthenticator
 */
class AccessTokenAuthenticator implements SimplePreAuthenticatorInterface
{

services.yml

# Authentication
mycompany_security.security.accesstoken_authenticator:
    class:     MyCompany\SBundle\Security\AccessTokenAuthenticator
    arguments: ["@mycompany_security.security.accesstoken_userprovider"]

Firewall Configuration :

secure_area:
    pattern:  ^/
    stateless: true
    simple_preauth:
        authenticator: mycompany_security.security.accesstoken_authenticator

My exact problem is even if I define two classes which are identical each other but the implementation namespace different even how could I give this to firewall ? How this can be abstracted from firewall ?

Any help would be appreciated.

  • 写回答

2条回答 默认 最新

  • duanruinong0619 2016-04-25 09:07
    关注

    OK I find the answer,

    When I focus the service container and security.yml firewall configurations. I just forget, my firewall configuration can be different from symfony2 and symfony3 application.

    In that manner I can would define a BaseAccessTokenAuthenticator and AccessTokenAuthenticator for either PreSymfony28 and Symfony30 and then I will put all the logic inside BaseAccessTokenAuthenticator and AccessTokenAuthenticator would be multiple and there would be 2 different service. One for symfony2.7 firewall configuration one for symfony3.0.

    Base Class :

    <?php
    
    namespace MyCompany\SBundle\Security;
    
    /**
     * Abstract Class BaseAccessTokenAuthenticator
     */
    abstract class BaseAccessTokenAuthenticator
    {
        public function createToken(Request $request, $providerKey)
        {
          // Implementation
        }
    
        public function authenticateToken(
            TokenInterface $token,
            UserProviderInterface $userProvider,
            $providerKey
        ) {
          // Implementation.
        }
    
        public function supportsToken(TokenInterface $token, $providerKey)
        {
          // Implementation.
        }
    }
    

    Symfony 3.0 class :

    <?php
    
    namespace MyCompany\SBundle\Security;
    
    use Symfony\Component\Security\Http\Authentication\SimplePreAuthenticatorInterface;
    
    /**
     * Class AccessTokenAuthenticatorSf30
     */
    class AccessTokenAuthenticatorSf30 extends BaseAccessTokenAuthenticator implements SimplePreAuthenticatorInterface
    {
    }
    

    Pre Symfony 2.8 class :

    <?php
    
    namespace MyCompany\SBundle\Security;
    
    use Symfony\Component\Security\Core\Authentication\SimplePreAuthenticatorInterface;
    
    /**
     * Class AccessTokenAuthenticatorPreSf28
     */
    class AccessTokenAuthenticatorPreSf28 extends BaseAccessTokenAuthenticator implements SimplePreAuthenticatorInterface
    {
    }
    

    Services :

    # Authentication
    mycompany.security.accesstoken_authenticator_pre_sf28:
        class:     MyCompany\SBundle\Security\AccessTokenAuthenticatorPreSf28
        arguments: ["@mycompany.security.accesstoken_userprovider"]
    
    # Authentication
    mycompany.security.accesstoken_authenticator_sf30:
        class:     MyCompany\SBundle\Security\AccessTokenAuthenticatorSf30
        arguments: ["@mycompany.security.accesstoken_userprovider"]
    

    wide application firewall for symfony =< 2.8 :

        simple_preauth:
            authenticator: mycompany.security.accesstoken_authenticator_sf28
    

    wide application firewall for symfony >= 2.8 :

        simple_preauth:
            authenticator: mycompany.security.accesstoken_authenticator_sf30
    
    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(1条)

报告相同问题?