[Security] Add simple_token auth method

This commit is contained in:
Jordi Boggiano 2013-04-12 13:49:16 +02:00
parent 1fe2ed64d1
commit f7a11a1ab3
9 changed files with 199 additions and 10 deletions

View File

@ -28,6 +28,8 @@ class SimpleFormFactory extends FormLoginFactory
$this->addOption('authenticator', null);
}
// TODO create proxies for success_handler/failure_handler that call the impl ones then the default ones by default if no response is returned
public function getKey()
{
return 'simple-form';

View File

@ -0,0 +1,64 @@
<?php
/*
* This file is part of the Symfony package.
*
* (c) Fabien Potencier <fabien@symfony.com>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace Symfony\Bundle\SecurityBundle\DependencyInjection\Security\Factory;
use Symfony\Component\Config\Definition\Builder\NodeDefinition;
use Symfony\Component\DependencyInjection\DefinitionDecorator;
use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\DependencyInjection\Reference;
/**
* @author Jordi Boggiano <j.boggiano@seld.be>
*/
class SimpleTokenFactory implements SecurityFactoryInterface
{
public function getPosition()
{
return 'http';
}
public function getKey()
{
return 'simple-token';
}
// TODO add support for success_handler/failure_handler that call the impl ones
public function addConfiguration(NodeDefinition $node)
{
$node
->children()
->scalarNode('provider')->end()
->scalarNode('authenticator')->cannotBeEmpty()->end()
->end()
;
}
public function create(ContainerBuilder $container, $id, $config, $userProvider, $defaultEntryPoint)
{
$provider = 'security.authentication.provider.simple_form.'.$id;
$container
->setDefinition($provider, new DefinitionDecorator('security.authentication.provider.simple'))
->replaceArgument(0, new Reference($config['authenticator']))
->replaceArgument(1, new Reference($userProvider))
->replaceArgument(2, $id)
;
// listener
$listenerId = 'security.authentication.listener.simple_token.'.$id;
$listener = $container->setDefinition($listenerId, new DefinitionDecorator('security.authentication.listener.simple_token'));
$listener->replaceArgument(2, $id);
$listener->replaceArgument(3, new Reference($config['authenticator']));
return array($provider, $listenerId);
}
}

View File

@ -14,6 +14,8 @@
<parameter key="security.authentication.listener.simple_form.class">Symfony\Component\Security\Http\Firewall\SimpleFormAuthenticationListener</parameter>
<parameter key="security.authentication.listener.simple_token.class">Symfony\Component\Security\Http\Firewall\SimpleTokenAuthenticationListener</parameter>
<parameter key="security.authentication.listener.basic.class">Symfony\Component\Security\Http\Firewall\BasicAuthenticationListener</parameter>
<parameter key="security.authentication.basic_entry_point.class">Symfony\Component\Security\Http\EntryPoint\BasicAuthenticationEntryPoint</parameter>
@ -142,6 +144,15 @@
abstract="true">
</service>
<service id="security.authentication.listener.simple_token" class="%security.authentication.listener.simple_token.class%" public="false" abstract="true">
<tag name="monolog.logger" channel="security" />
<argument type="service" id="security.context" />
<argument type="service" id="security.authentication.manager" />
<argument /> <!-- Provider-shared Key -->
<argument /> <!-- Authenticator -->
<argument type="service" id="logger" on-invalid="null" />
</service>
<service id="security.authentication.listener.x509" class="%security.authentication.listener.x509.class%" public="false" abstract="true">
<tag name="monolog.logger" channel="security" />
<argument type="service" id="security.context" />

View File

@ -19,6 +19,7 @@ use Symfony\Bundle\SecurityBundle\DependencyInjection\Security\Factory\HttpBasic
use Symfony\Bundle\SecurityBundle\DependencyInjection\Security\Factory\HttpDigestFactory;
use Symfony\Bundle\SecurityBundle\DependencyInjection\Security\Factory\RememberMeFactory;
use Symfony\Bundle\SecurityBundle\DependencyInjection\Security\Factory\X509Factory;
use Symfony\Bundle\SecurityBundle\DependencyInjection\Security\Factory\SimpleTokenFactory;
use Symfony\Bundle\SecurityBundle\DependencyInjection\Security\Factory\SimpleFormFactory;
use Symfony\Bundle\SecurityBundle\DependencyInjection\Security\UserProvider\InMemoryFactory;
@ -39,6 +40,7 @@ class SecurityBundle extends Bundle
$extension->addSecurityListenerFactory(new HttpDigestFactory());
$extension->addSecurityListenerFactory(new RememberMeFactory());
$extension->addSecurityListenerFactory(new X509Factory());
$extension->addSecurityListenerFactory(new SimpleTokenFactory());
$extension->addSecurityListenerFactory(new SimpleFormFactory());
$extension->addUserProviderFactory(new InMemoryFactory());

View File

@ -40,7 +40,7 @@ class SimpleAuthenticationProvider implements AuthenticationProviderInterface
public function authenticate(TokenInterface $token)
{
$authToken = $this->simpleAuthenticator->authenticate($token, $this->userProvider, $this->providerKey);
$authToken = $this->simpleAuthenticator->authenticateToken($token, $this->userProvider, $this->providerKey);
if ($authToken instanceof TokenInterface) {
return $authToken;
@ -51,6 +51,6 @@ class SimpleAuthenticationProvider implements AuthenticationProviderInterface
public function supports(TokenInterface $token)
{
return $this->simpleAuthenticator->supports($token, $this->providerKey);
return $this->simpleAuthenticator->supportsToken($token, $this->providerKey);
}
}

View File

@ -13,18 +13,19 @@ namespace Symfony\Component\Security\Core\Authentication;
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
use Symfony\Component\Security\Core\Exception\AuthenticationException;
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\Security\Core\User\UserProviderInterface;
use Symfony\Component\HttpFoundation\Request;
/**
* @author Jordi Boggiano <j.boggiano@seld.be>
*/
interface SimpleAuthenticatorInterface
{
public function authenticate(TokenInterface $token, UserProviderInterface $userProvider, $providerKey);
public function authenticateToken(TokenInterface $token, UserProviderInterface $userProvider, $providerKey);
public function supports(TokenInterface $token, $providerKey);
public function supportsToken(TokenInterface $token, $providerKey);
public function handleAuthenticationFailure(GetResponseEvent $event, AuthenticationException $exception);
public function onAuthenticationFailure(Request $request, AuthenticationException $exception);
public function onAuthenticationSuccess(Request $request, TokenInterface $token);
}

View File

@ -11,9 +11,6 @@
namespace Symfony\Component\Security\Core\Authentication;
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
use Symfony\Component\Security\Core\Exception\AuthenticationException;
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
use Symfony\Component\HttpFoundation\Request;
/**

View File

@ -0,0 +1,22 @@
<?php
/*
* This file is part of the Symfony package.
*
* (c) Fabien Potencier <fabien@symfony.com>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace Symfony\Component\Security\Core\Authentication;
use Symfony\Component\HttpFoundation\Request;
/**
* @author Jordi Boggiano <j.boggiano@seld.be>
*/
interface SimpleTokenAuthenticatorInterface extends SimpleAuthenticatorInterface
{
public function createToken(Request $request, $providerKey);
}

View File

@ -0,0 +1,90 @@
<?php
/*
* This file is part of the Symfony package.
*
* (c) Fabien Potencier <fabien@symfony.com>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace Symfony\Component\Security\Http\Firewall;
use Symfony\Component\Security\Core\SecurityContextInterface;
use Symfony\Component\Security\Core\Authentication\AuthenticationManagerInterface;
use Symfony\Component\Security\Http\EntryPoint\AuthenticationEntryPointInterface;
use Psr\Log\LoggerInterface;
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
use Symfony\Component\Security\Core\Authentication\SimpleTokenAuthenticatorInterface;
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
use Symfony\Component\Security\Core\Exception\AuthenticationException;
/**
* SimpleTokenListener implements simple proxying to an authenticator.
*
* @author Jordi Boggiano <j.boggiano@seld.be>
*/
class SimpleTokenAuthenticationListener implements ListenerInterface
{
private $securityContext;
private $authenticationManager;
private $providerKey;
private $simpleAuthenticator;
private $logger;
/**
* Constructor.
*
* @param SecurityContextInterface $securityContext A SecurityContext instance
* @param AuthenticationManagerInterface $authenticationManager An AuthenticationManagerInterface instance
* @param string $providerKey
* @param SimpleTokenAuthenticatorInterface $simpleAuthenticator A SimpleTokenAuthenticatorInterface instance
* @param LoggerInterface $logger A LoggerInterface instance
*/
public function __construct(SecurityContextInterface $securityContext, AuthenticationManagerInterface $authenticationManager, $providerKey, SimpleTokenAuthenticatorInterface $simpleAuthenticator, LoggerInterface $logger = null)
{
if (empty($providerKey)) {
throw new \InvalidArgumentException('$providerKey must not be empty.');
}
$this->securityContext = $securityContext;
$this->authenticationManager = $authenticationManager;
$this->providerKey = $providerKey;
$this->simpleAuthenticator = $simpleAuthenticator;
$this->logger = $logger;
}
/**
* Handles basic authentication.
*
* @param GetResponseEvent $event A GetResponseEvent instance
*/
public function handle(GetResponseEvent $event)
{
$request = $event->getRequest();
if (null !== $this->logger) {
$this->logger->info(sprintf('Attempting simple token authorization %s', $this->providerKey));
}
try {
$token = $this->simpleAuthenticator->createToken($request, $this->providerKey);
$token = $this->authenticationManager->authenticate($token);
$this->securityContext->setToken($token);
} catch (AuthenticationException $failed) {
$this->securityContext->setToken(null);
if (null !== $this->logger) {
$this->logger->info(sprintf('Authentication request failed: %s', $failed->getMessage()));
}
// TODO call failure handler
return;
}
// TODO call success handler
}
}