diff options
54 files changed, 557 insertions, 340 deletions
diff --git a/CHANGELOG.md b/CHANGELOG.md index 92f8073..6802055 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,13 @@ CHANGELOG ========= +2.4.0 +----- + + * The switch user listener now preserves the query string when switching a user + * The remember-me cookie hashes now use HMAC, which means that current cookies will be invalidated + * added simpler customization options + 2.3.0 ----- diff --git a/Core/Authentication/Provider/SimpleAuthenticationProvider.php b/Core/Authentication/Provider/SimpleAuthenticationProvider.php new file mode 100644 index 0000000..8f8cceb --- /dev/null +++ b/Core/Authentication/Provider/SimpleAuthenticationProvider.php @@ -0,0 +1,56 @@ +<?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\Provider; + +use Symfony\Component\Security\Core\Encoder\EncoderFactoryInterface; +use Symfony\Component\Security\Core\User\UserProviderInterface; +use Symfony\Component\Security\Core\User\UserCheckerInterface; +use Symfony\Component\Security\Core\User\UserInterface; +use Symfony\Component\Security\Core\Exception\UsernameNotFoundException; +use Symfony\Component\Security\Core\Exception\AuthenticationServiceException; +use Symfony\Component\Security\Core\Exception\BadCredentialsException; +use Symfony\Component\Security\Core\Authentication\Token\TokenInterface; +use Symfony\Component\Security\Core\Authentication\SimpleAuthenticatorInterface; +use Symfony\Component\Security\Core\Exception\AuthenticationException; + +/** + * @author Jordi Boggiano <j.boggiano@seld.be> + */ +class SimpleAuthenticationProvider implements AuthenticationProviderInterface +{ + private $simpleAuthenticator; + private $userProvider; + private $providerKey; + + public function __construct(SimpleAuthenticatorInterface $simpleAuthenticator, UserProviderInterface $userProvider, $providerKey) + { + $this->simpleAuthenticator = $simpleAuthenticator; + $this->userProvider = $userProvider; + $this->providerKey = $providerKey; + } + + public function authenticate(TokenInterface $token) + { + $authToken = $this->simpleAuthenticator->authenticateToken($token, $this->userProvider, $this->providerKey); + + if ($authToken instanceof TokenInterface) { + return $authToken; + } + + throw new AuthenticationException('Simple authenticator failed to return an authenticated token.'); + } + + public function supports(TokenInterface $token) + { + return $this->simpleAuthenticator->supportsToken($token, $this->providerKey); + } +} diff --git a/Core/Authentication/SimpleAuthenticatorInterface.php b/Core/Authentication/SimpleAuthenticatorInterface.php new file mode 100644 index 0000000..868d072 --- /dev/null +++ b/Core/Authentication/SimpleAuthenticatorInterface.php @@ -0,0 +1,25 @@ +<?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\Security\Core\Authentication\Token\TokenInterface; +use Symfony\Component\Security\Core\User\UserProviderInterface; + +/** + * @author Jordi Boggiano <j.boggiano@seld.be> + */ +interface SimpleAuthenticatorInterface +{ + public function authenticateToken(TokenInterface $token, UserProviderInterface $userProvider, $providerKey); + + public function supportsToken(TokenInterface $token, $providerKey); +} diff --git a/Core/Authentication/SimpleFormAuthenticatorInterface.php b/Core/Authentication/SimpleFormAuthenticatorInterface.php new file mode 100644 index 0000000..95ee881 --- /dev/null +++ b/Core/Authentication/SimpleFormAuthenticatorInterface.php @@ -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 SimpleFormAuthenticatorInterface extends SimpleAuthenticatorInterface +{ + public function createToken(Request $request, $username, $password, $providerKey); +} diff --git a/Core/Authentication/SimplePreAuthenticatorInterface.php b/Core/Authentication/SimplePreAuthenticatorInterface.php new file mode 100644 index 0000000..6164e7d --- /dev/null +++ b/Core/Authentication/SimplePreAuthenticatorInterface.php @@ -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 SimplePreAuthenticatorInterface extends SimpleAuthenticatorInterface +{ + public function createToken(Request $request, $providerKey); +} diff --git a/Core/Authentication/Token/AbstractToken.php b/Core/Authentication/Token/AbstractToken.php index 1d65819..c532532 100644 --- a/Core/Authentication/Token/AbstractToken.php +++ b/Core/Authentication/Token/AbstractToken.php @@ -208,7 +208,7 @@ abstract class AbstractToken implements TokenInterface } /** - * Sets a attribute. + * Sets an attribute. * * @param string $name The attribute name * @param mixed $value The attribute value diff --git a/Core/Authorization/AccessDecisionManager.php b/Core/Authorization/AccessDecisionManager.php index 6028c42..18c3569 100644 --- a/Core/Authorization/AccessDecisionManager.php +++ b/Core/Authorization/AccessDecisionManager.php @@ -43,8 +43,13 @@ class AccessDecisionManager implements AccessDecisionManagerInterface throw new \InvalidArgumentException('You must at least add one voter.'); } + $strategyMethod = 'decide'.ucfirst($strategy); + if (!is_callable(array($this, $strategyMethod))) { + throw new \InvalidArgumentException(sprintf('The strategy "%s" is not supported.', $strategy)); + } + $this->voters = $voters; - $this->strategy = 'decide'.ucfirst($strategy); + $this->strategy = $strategyMethod; $this->allowIfAllAbstainDecisions = (Boolean) $allowIfAllAbstainDecisions; $this->allowIfEqualGrantedDeniedDecisions = (Boolean) $allowIfEqualGrantedDeniedDecisions; } diff --git a/Http/Authentication/SimpleAuthenticationHandler.php b/Http/Authentication/SimpleAuthenticationHandler.php new file mode 100644 index 0000000..ce56ee3 --- /dev/null +++ b/Http/Authentication/SimpleAuthenticationHandler.php @@ -0,0 +1,105 @@ +<?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\Authentication; + +use Symfony\Component\HttpFoundation\Request; +use Symfony\Component\HttpFoundation\Response; +use Psr\Log\LoggerInterface; +use Symfony\Component\Security\Core\Exception\AuthenticationException; +use Symfony\Component\Security\Core\Authentication\Token\TokenInterface; +use Symfony\Component\Security\Core\Authentication\SimpleAuthenticatorInterface; + +/** + * Class to proxy authentication success/failure handlers + * + * Events are sent to the SimpleAuthenticatorInterface if it implements + * the right interface, otherwise (or if it fails to return a Response) + * the default handlers are triggered. + * + * @author Jordi Boggiano <j.boggiano@seld.be> + */ +class SimpleAuthenticationHandler implements AuthenticationFailureHandlerInterface, AuthenticationSuccessHandlerInterface +{ + protected $successHandler; + protected $failureHandler; + protected $simpleAuthenticator; + + /** + * Constructor. + * + * @param SimpleAuthenticatorInterface $authenticator SimpleAuthenticatorInterface instance + * @param AuthenticationSuccessHandlerInterface $successHandler Default success handler + * @param AuthenticationFailureHandlerInterface $failureHandler Default failure handler + * @param LoggerInterface $logger Optional logger + */ + public function __construct(SimpleAuthenticatorInterface $authenticator, AuthenticationSuccessHandlerInterface $successHandler, AuthenticationFailureHandlerInterface $failureHandler, LoggerInterface $logger = null) + { + $this->simpleAuthenticator = $authenticator; + $this->successHandler = $successHandler; + $this->failureHandler = $failureHandler; + $this->logger = $logger; + } + + /** + * {@inheritDoc} + */ + public function onAuthenticationSuccess(Request $request, TokenInterface $token) + { + if ($this->simpleAuthenticator instanceof AuthenticationSuccessHandlerInterface) { + if ($this->logger) { + $this->logger->debug(sprintf('Using the %s object as authentication success handler', get_class($this->simpleAuthenticator))); + } + + $response = $this->simpleAuthenticator->onAuthenticationSuccess($request, $token); + if ($response instanceof Response) { + return $response; + } + + if (null !== $response) { + throw new \UnexpectedValueException(sprintf('The %s::onAuthenticationSuccess method must return null to use the default success handler, or a Response object', get_class($this->simpleAuthenticator))); + } + } + + if ($this->logger) { + $this->logger->debug('Fallback to the default authentication success handler'); + } + + return $this->successHandler->onAuthenticationSuccess($request, $token); + } + + /** + * {@inheritDoc} + */ + public function onAuthenticationFailure(Request $request, AuthenticationException $exception) + { + if ($this->simpleAuthenticator instanceof AuthenticationFailureHandlerInterface) { + if ($this->logger) { + $this->logger->debug(sprintf('Using the %s object as authentication failure handler', get_class($this->simpleAuthenticator))); + } + + $response = $this->simpleAuthenticator->onAuthenticationFailure($request, $exception); + if ($response instanceof Response) { + return $response; + } + + if (null !== $response) { + throw new \UnexpectedValueException(sprintf('The %s::onAuthenticationFailure method must return null to use the default failure handler, or a Response object', get_class($this->simpleAuthenticator))); + } + } + + if ($this->logger) { + $this->logger->debug('Fallback to the default authentication failure handler'); + } + + return $this->failureHandler->onAuthenticationFailure($request, $exception); + } +} diff --git a/Http/Firewall.php b/Http/Firewall.php index 31c1da5..5a1e9d5 100644 --- a/Http/Firewall.php +++ b/Http/Firewall.php @@ -11,9 +11,9 @@ namespace Symfony\Component\Security\Http; -use Symfony\Component\HttpKernel\HttpKernelInterface; use Symfony\Component\HttpKernel\KernelEvents; use Symfony\Component\HttpKernel\Event\GetResponseEvent; +use Symfony\Component\HttpKernel\Event\FinishRequestEvent; use Symfony\Component\EventDispatcher\EventDispatcherInterface; use Symfony\Component\EventDispatcher\EventSubscriberInterface; @@ -31,6 +31,7 @@ class Firewall implements EventSubscriberInterface { private $map; private $dispatcher; + private $exceptionListeners; /** * Constructor. @@ -42,6 +43,7 @@ class Firewall implements EventSubscriberInterface { $this->map = $map; $this->dispatcher = $dispatcher; + $this->exceptionListeners = new \SplObjectStorage(); } /** @@ -51,13 +53,14 @@ class Firewall implements EventSubscriberInterface */ public function onKernelRequest(GetResponseEvent $event) { - if (HttpKernelInterface::MASTER_REQUEST !== $event->getRequestType()) { + if (!$event->isMasterRequest()) { return; } // register listeners for this firewall list($listeners, $exception) = $this->map->getListeners($event->getRequest()); if (null !== $exception) { + $this->exceptionListeners[$event->getRequest()] = $exception; $exception->register($this->dispatcher); } @@ -71,8 +74,21 @@ class Firewall implements EventSubscriberInterface } } + public function onKernelFinishRequest(FinishRequestEvent $event) + { + $request = $event->getRequest(); + + if (isset($this->exceptionListeners[$request])) { + $this->exceptionListeners[$request]->unregister($this->dispatcher); + unset($this->exceptionListeners[$request]); + } + } + public static function getSubscribedEvents() { - return array(KernelEvents::REQUEST => array('onKernelRequest', 8)); + return array( + KernelEvents::REQUEST => array('onKernelRequest', 8), + KernelEvents::FINISH_REQUEST => 'onKernelFinishRequest', + ); } } diff --git a/Http/Firewall/ContextListener.php b/Http/Firewall/ContextListener.php index 81ccbdc..2db79f3 100644 --- a/Http/Firewall/ContextListener.php +++ b/Http/Firewall/ContextListener.php @@ -11,7 +11,6 @@ namespace Symfony\Component\Security\Http\Firewall; -use Symfony\Component\HttpKernel\HttpKernelInterface; use Psr\Log\LoggerInterface; use Symfony\Component\HttpKernel\Event\GetResponseEvent; use Symfony\Component\HttpKernel\Event\FilterResponseEvent; @@ -66,7 +65,7 @@ class ContextListener implements ListenerInterface */ public function handle(GetResponseEvent $event) { - if (!$this->registered && null !== $this->dispatcher && HttpKernelInterface::MASTER_REQUEST === $event->getRequestType()) { + if (!$this->registered && null !== $this->dispatcher && $event->isMasterRequest()) { $this->dispatcher->addListener(KernelEvents::RESPONSE, array($this, 'onKernelResponse')); $this->registered = true; } @@ -106,7 +105,7 @@ class ContextListener implements ListenerInterface */ public function onKernelResponse(FilterResponseEvent $event) { - if (HttpKernelInterface::MASTER_REQUEST !== $event->getRequestType()) { + if (!$event->isMasterRequest()) { return; } diff --git a/Http/Firewall/ExceptionListener.php b/Http/Firewall/ExceptionListener.php index abbb460..0cca0c4 100644 --- a/Http/Firewall/ExceptionListener.php +++ b/Http/Firewall/ExceptionListener.php @@ -70,16 +70,22 @@ class ExceptionListener } /** + * Unregisters the dispatcher. + * + * @param EventDispatcherInterface $dispatcher An EventDispatcherInterface instance + */ + public function unregister(EventDispatcherInterface $dispatcher) + { + $dispatcher->removeListener(KernelEvents::EXCEPTION, array($this, 'onKernelException')); + } + + /** * Handles security related exceptions. * * @param GetResponseForExceptionEvent $event An GetResponseForExceptionEvent instance */ public function onKernelException(GetResponseForExceptionEvent $event) { - // we need to remove ourselves as the exception listener can be - // different depending on the Request - $event->getDispatcher()->removeListener(KernelEvents::EXCEPTION, array($this, 'onKernelException')); - $exception = $event->getException(); $request = $event->getRequest(); diff --git a/Http/Firewall/SimpleFormAuthenticationListener.php b/Http/Firewall/SimpleFormAuthenticationListener.php new file mode 100644 index 0000000..7c4b971 --- /dev/null +++ b/Http/Firewall/SimpleFormAuthenticationListener.php @@ -0,0 +1,116 @@ +<?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\EventDispatcher\EventDispatcherInterface; +use Symfony\Component\HttpKernel\Event\GetResponseEvent; +use Symfony\Component\HttpFoundation\Request; +use Symfony\Component\Security\Http\Authentication\AuthenticationFailureHandlerInterface; +use Symfony\Component\Security\Http\Authentication\AuthenticationSuccessHandlerInterface; +use Symfony\Component\Security\Core\Authentication\AuthenticationManagerInterface; +use Symfony\Component\Form\Extension\Csrf\CsrfProvider\CsrfProviderInterface; +use Symfony\Component\Security\Core\Authentication\SimpleFormAuthenticatorInterface; +use Symfony\Component\Security\Core\Authentication\Token\TokenInterface; +use Symfony\Component\Security\Core\Exception\AuthenticationException; +use Symfony\Component\Security\Core\Exception\SessionUnavailableException; +use Symfony\Component\Security\Core\SecurityContextInterface; +use Symfony\Component\Security\Http\Event\InteractiveLoginEvent; +use Symfony\Component\Security\Http\HttpUtils; +use Symfony\Component\Security\Http\RememberMe\RememberMeServicesInterface; +use Symfony\Component\Security\Http\SecurityEvents; +use Symfony\Component\Security\Http\Session\SessionAuthenticationStrategyInterface; +use Psr\Log\LoggerInterface; + +/** + * @author Jordi Boggiano <j.boggiano@seld.be> + */ +class SimpleFormAuthenticationListener extends AbstractAuthenticationListener +{ + private $simpleAuthenticator; + private $csrfProvider; + + /** + * Constructor. + * + * @param SecurityContextInterface $securityContext A SecurityContext instance + * @param AuthenticationManagerInterface $authenticationManager An AuthenticationManagerInterface instance + * @param SessionAuthenticationStrategyInterface $sessionStrategy + * @param HttpUtils $httpUtils An HttpUtilsInterface instance + * @param string $providerKey + * @param AuthenticationSuccessHandlerInterface $successHandler + * @param AuthenticationFailureHandlerInterface $failureHandler + * @param array $options An array of options for the processing of a + * successful, or failed authentication attempt + * @param LoggerInterface $logger A LoggerInterface instance + * @param EventDispatcherInterface $dispatcher An EventDispatcherInterface instance + * @param SimpleFormAuthenticatorInterface $simpleAuthenticator A SimpleFormAuthenticatorInterface instance + * @param CsrfProviderInterface $csrfProvider A CsrfProviderInterface instance + */ + public function __construct(SecurityContextInterface $securityContext, AuthenticationManagerInterface $authenticationManager, SessionAuthenticationStrategyInterface $sessionStrategy, HttpUtils $httpUtils, $providerKey, AuthenticationSuccessHandlerInterface $successHandler, AuthenticationFailureHandlerInterface $failureHandler, array $options = array(), LoggerInterface $logger = null, EventDispatcherInterface $dispatcher = null, CsrfProviderInterface $csrfProvider = null, SimpleFormAuthenticatorInterface $simpleAuthenticator = null) + { + if (!$simpleAuthenticator) { + throw new \InvalidArgumentException('Missing simple authenticator'); + } + + $this->simpleAuthenticator = $simpleAuthenticator; + $this->csrfProvider = $csrfProvider; + + $options = array_merge(array( + 'username_parameter' => '_username', + 'password_parameter' => '_password', + 'csrf_parameter' => '_csrf_token', + 'intention' => 'authenticate', + 'post_only' => true, + ), $options); + parent::__construct($securityContext, $authenticationManager, $sessionStrategy, $httpUtils, $providerKey, $successHandler, $failureHandler, $options, $logger, $dispatcher); + } + + /** + * {@inheritdoc} + */ + protected function requiresAuthentication(Request $request) + { + if ($this->options['post_only'] && !$request->isMethod('POST')) { + return false; + } + + return parent::requiresAuthentication($request); + } + + /** + * {@inheritdoc} + */ + protected function attemptAuthentication(Request $request) + { + if (null !== $this->csrfProvider) { + $csrfToken = $request->get($this->options['csrf_parameter'], null, true); + + if (false === $this->csrfProvider->isCsrfTokenValid($this->options['intention'], $csrfToken)) { + throw new InvalidCsrfTokenException('Invalid CSRF token.'); + } + } + + if ($this->options['post_only']) { + $username = trim($request->request->get($this->options['username_parameter'], null, true)); + $password = $request->request->get($this->options['password_parameter'], null, true); + } else { + $username = trim($request->get($this->options['username_parameter'], null, true)); + $password = $request->get($this->options['password_parameter'], null, true); + } + + $request->getSession()->set(SecurityContextInterface::LAST_USERNAME, $username); + + $token = $this->simpleAuthenticator->createToken($request, $username, $password, $this->providerKey); + + return $this->authenticationManager->authenticate($token); + } +} diff --git a/Http/Firewall/SimplePreAuthenticationListener.php b/Http/Firewall/SimplePreAuthenticationListener.php new file mode 100644 index 0000000..2a6b4d5 --- /dev/null +++ b/Http/Firewall/SimplePreAuthenticationListener.php @@ -0,0 +1,111 @@ +<?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\HttpFoundation\Response; +use Symfony\Component\Security\Core\Authentication\SimplePreAuthenticatorInterface; +use Symfony\Component\Security\Core\Authentication\Token\TokenInterface; +use Symfony\Component\Security\Core\Authentication\Token\AnonymousToken; +use Symfony\Component\Security\Core\Exception\AuthenticationException; +use Symfony\Component\Security\Http\Authentication\AuthenticationFailureHandlerInterface; +use Symfony\Component\Security\Http\Authentication\AuthenticationSuccessHandlerInterface; + +/** + * SimplePreAuthenticationListener implements simple proxying to an authenticator. + * + * @author Jordi Boggiano <j.boggiano@seld.be> + */ +class SimplePreAuthenticationListener 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 SimplePreAuthenticatorInterface $simpleAuthenticator A SimplePreAuthenticatorInterface instance + * @param LoggerInterface $logger A LoggerInterface instance + */ + public function __construct(SecurityContextInterface $securityContext, AuthenticationManagerInterface $authenticationManager, $providerKey, SimplePreAuthenticatorInterface $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 pre-authorization %s', $this->providerKey)); + } + + if (null !== $this->context->getToken() && !$this->context->getToken() instanceof AnonymousToken) { + return; + } + + try { + $token = $this->simpleAuthenticator->createToken($request, $this->providerKey); + $token = $this->authenticationManager->authenticate($token); + $this->securityContext->setToken($token); + } catch (AuthenticationException $e) { + $this->securityContext->setToken(null); + + if (null !== $this->logger) { + $this->logger->info(sprintf('Authentication request failed: %s', $e->getMessage())); + } + + if ($this->simpleAuthenticator instanceof AuthenticationFailureHandlerInterface) { + $response = $this->simpleAuthenticator->onAuthenticationFailure($request, $e); + if ($response instanceof Response) { + $event->setResponse($response); + } elseif (null !== $response) { + throw new \UnexpectedValueException(sprintf('The %s::onAuthenticationFailure method must return null or a Response object', get_class($this->simpleAuthenticator))); + } + } + + return; + } + + if ($this->simpleAuthenticator instanceof AuthenticationSuccessHandlerInterface) { + $response = $this->simpleAuthenticator->onAuthenticationSuccess($request, $token); + if ($response instanceof Response) { + $event->setResponse($response); + } elseif (null !== $response) { + throw new \UnexpectedValueException(sprintf('The %s::onAuthenticationSuccess method must return null or a Response object', get_class($this->simpleAuthenticator))); + } + } + } +} diff --git a/Http/Firewall/SwitchUserListener.php b/Http/Firewall/SwitchUserListener.php index 7700096..b46b1bc 100644 --- a/Http/Firewall/SwitchUserListener.php +++ b/Http/Firewall/SwitchUserListener.php @@ -92,7 +92,9 @@ class SwitchUserListener implements ListenerInterface } } - $request->server->set('QUERY_STRING', ''); + $request->query->remove($this->usernameParameter); + $request->server->set('QUERY_STRING', http_build_query($request->query->all())); + $response = new RedirectResponse($request->getUri(), 302); $event->setResponse($response); diff --git a/Http/RememberMe/TokenBasedRememberMeServices.php b/Http/RememberMe/TokenBasedRememberMeServices.php index 5a66fe4..995b6f6 100644 --- a/Http/RememberMe/TokenBasedRememberMeServices.php +++ b/Http/RememberMe/TokenBasedRememberMeServices.php @@ -147,6 +147,6 @@ class TokenBasedRememberMeServices extends AbstractRememberMeServices */ protected function generateCookieHash($class, $username, $expires, $password) { - return hash('sha256', $class.$username.$expires.$password.$this->getKey()); + return hash_hmac('sha256', $class.$username.$expires.$password, $this->getKey()); } } @@ -11,7 +11,7 @@ Resources Documentation: -http://symfony.com/doc/2.3/book/security.html +http://symfony.com/doc/2.4/book/security.html Resources --------- diff --git a/Tests/Acl/Dbal/AclProviderBenchmarkTest.php b/Tests/Acl/Dbal/AclProviderBenchmarkTest.php index 8f6a30c..f6e3ba8 100644 --- a/Tests/Acl/Dbal/AclProviderBenchmarkTest.php +++ b/Tests/Acl/Dbal/AclProviderBenchmarkTest.php @@ -32,10 +32,6 @@ class AclProviderBenchmarkTest extends \PHPUnit_Framework_TestCase protected function setUp() { - if (!class_exists('Doctrine\DBAL\DriverManager')) { - $this->markTestSkipped('The "Doctrine DBAL" library is not available'); - } - try { $this->con = DriverManager::getConnection(array( 'driver' => 'pdo_mysql', diff --git a/Tests/Acl/Dbal/AclProviderTest.php b/Tests/Acl/Dbal/AclProviderTest.php index ad58d72..d701e22 100644 --- a/Tests/Acl/Dbal/AclProviderTest.php +++ b/Tests/Acl/Dbal/AclProviderTest.php @@ -141,9 +141,6 @@ class AclProviderTest extends \PHPUnit_Framework_TestCase protected function setUp() { - if (!class_exists('Doctrine\DBAL\DriverManager')) { - $this->markTestSkipped('The Doctrine2 DBAL is required for this test'); - } if (!class_exists('PDO') || !in_array('sqlite', \PDO::getAvailableDrivers())) { self::markTestSkipped('This test requires SQLite support in your environment'); } diff --git a/Tests/Acl/Dbal/MutableAclProviderTest.php b/Tests/Acl/Dbal/MutableAclProviderTest.php index 3e8d65f..69778c9 100644 --- a/Tests/Acl/Dbal/MutableAclProviderTest.php +++ b/Tests/Acl/Dbal/MutableAclProviderTest.php @@ -429,9 +429,6 @@ class MutableAclProviderTest extends \PHPUnit_Framework_TestCase protected function setUp() { - if (!class_exists('Doctrine\DBAL\DriverManager')) { - $this->markTestSkipped('The Doctrine2 DBAL is required for this test'); - } if (!class_exists('PDO') || !in_array('sqlite', \PDO::getAvailableDrivers())) { self::markTestSkipped('This test requires SQLite support in your environment'); } diff --git a/Tests/Acl/Domain/AclTest.php b/Tests/Acl/Domain/AclTest.php index 4b67e62..390bebf 100644 --- a/Tests/Acl/Domain/AclTest.php +++ b/Tests/Acl/Domain/AclTest.php @@ -511,11 +511,4 @@ class AclTest extends \PHPUnit_Framework_TestCase { return new Acl(1, new ObjectIdentity(1, 'foo'), new PermissionGrantingStrategy(), array(), true); } - - protected function setUp() - { - if (!class_exists('Doctrine\DBAL\DriverManager')) { - $this->markTestSkipped('The Doctrine2 DBAL is required for this test'); - } - } } diff --git a/Tests/Acl/Domain/DoctrineAclCacheTest.php b/Tests/Acl/Domain/DoctrineAclCacheTest.php index 99eb27e..93c87c1 100644 --- a/Tests/Acl/Domain/DoctrineAclCacheTest.php +++ b/Tests/Acl/Domain/DoctrineAclCacheTest.php @@ -98,11 +98,4 @@ class DoctrineAclCacheTest extends \PHPUnit_Framework_TestCase return new DoctrineAclCache($cacheDriver, $this->getPermissionGrantingStrategy(), $prefix); } - - protected function setUp() - { - if (!class_exists('Doctrine\DBAL\DriverManager')) { - $this->markTestSkipped('The Doctrine2 DBAL is required for this test'); - } - } } diff --git a/Tests/Acl/Domain/ObjectIdentityTest.php b/Tests/Acl/Domain/ObjectIdentityTest.php index 7aa3cf2..9281fd5 100644 --- a/Tests/Acl/Domain/ObjectIdentityTest.php +++ b/Tests/Acl/Domain/ObjectIdentityTest.php @@ -85,13 +85,6 @@ namespace Symfony\Component\Security\Tests\Acl\Domain array(new ObjectIdentity('1', 'bla'), new ObjectIdentity('1', 'blub'), false), ); } - - protected function setUp() - { - if (!class_exists('Doctrine\DBAL\DriverManager')) { - $this->markTestSkipped('The Doctrine2 DBAL is required for this test'); - } - } } class TestDomainObject diff --git a/Tests/Acl/Domain/PermissionGrantingStrategyTest.php b/Tests/Acl/Domain/PermissionGrantingStrategyTest.php index d200d2b..964aa1f 100644 --- a/Tests/Acl/Domain/PermissionGrantingStrategyTest.php +++ b/Tests/Acl/Domain/PermissionGrantingStrategyTest.php @@ -182,11 +182,4 @@ class PermissionGrantingStrategyTest extends \PHPUnit_Framework_TestCase return new Acl($id++, new ObjectIdentity(1, 'Foo'), $strategy, array(), true); } - - protected function setUp() - { - if (!class_exists('Doctrine\DBAL\DriverManager')) { - $this->markTestSkipped('The Doctrine2 DBAL is required for this test'); - } - } } diff --git a/Tests/Core/Authorization/AccessDecisionManagerTest.php b/Tests/Core/Authorization/AccessDecisionManagerTest.php index 1c706cc..ead97d2 100644 --- a/Tests/Core/Authorization/AccessDecisionManagerTest.php +++ b/Tests/Core/Authorization/AccessDecisionManagerTest.php @@ -55,6 +55,14 @@ class AccessDecisionManagerTest extends \PHPUnit_Framework_TestCase } /** + * @expectedException \InvalidArgumentException + */ + public function testSetUnsupportedStrategy() + { + new AccessDecisionManager(array($this->getVoter(VoterInterface::ACCESS_GRANTED)), 'fooBar'); + } + + /** * @dataProvider getStrategyTests */ public function testStrategies($strategy, $voters, $allowIfAllAbstainDecisions, $allowIfEqualGrantedDeniedDecisions, $expected) diff --git a/Tests/Core/Validator/Constraints/UserPasswordValidatorTest.php b/Tests/Core/Validator/Constraints/UserPasswordValidatorTest.php index c3a8370..93bff3c 100644 --- a/Tests/Core/Validator/Constraints/UserPasswordValidatorTest.php +++ b/Tests/Core/Validator/Constraints/UserPasswordValidatorTest.php @@ -23,10 +23,6 @@ class UserPasswordValidatorTest extends \PHPUnit_Framework_TestCase protected function setUp() { - if (false === class_exists('Symfony\Component\Validator\Validator')) { - $this->markTestSkipped('The Validator component is required for this test.'); - } - $this->context = $this->getMock('Symfony\Component\Validator\ExecutionContext', array(), array(), '', false); } diff --git a/Tests/Http/AccessMapTest.php b/Tests/Http/AccessMapTest.php index 653152a..c2d9b7f 100644 --- a/Tests/Http/AccessMapTest.php +++ b/Tests/Http/AccessMapTest.php @@ -15,13 +15,6 @@ use Symfony\Component\Security\Http\AccessMap; class AccessMapTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testReturnsFirstMatchedPattern() { $request = $this->getMock('Symfony\Component\HttpFoundation\Request'); diff --git a/Tests/Http/Authentication/DefaultAuthenticationFailureHandlerTest.php b/Tests/Http/Authentication/DefaultAuthenticationFailureHandlerTest.php index c51893f..b741ced 100644 --- a/Tests/Http/Authentication/DefaultAuthenticationFailureHandlerTest.php +++ b/Tests/Http/Authentication/DefaultAuthenticationFailureHandlerTest.php @@ -31,18 +31,6 @@ class DefaultAuthenticationFailureHandlerTest extends \PHPUnit_Framework_TestCas protected function setUp() { - if (!class_exists('Symfony\Component\HttpKernel\HttpKernel')) { - $this->markTestSkipped('The "HttpKernel" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!interface_exists('Psr\Log\LoggerInterface')) { - $this->markTestSkipped('The "LoggerInterface" is not available'); - } - $this->httpKernel = $this->getMock('Symfony\Component\HttpKernel\HttpKernelInterface'); $this->httpUtils = $this->getMock('Symfony\Component\Security\Http\HttpUtils'); $this->logger = $this->getMock('Psr\Log\LoggerInterface'); diff --git a/Tests/Http/Authentication/DefaultAuthenticationSuccessHandlerTest.php b/Tests/Http/Authentication/DefaultAuthenticationSuccessHandlerTest.php index 71d6ad4..3ba6a17 100644 --- a/Tests/Http/Authentication/DefaultAuthenticationSuccessHandlerTest.php +++ b/Tests/Http/Authentication/DefaultAuthenticationSuccessHandlerTest.php @@ -23,10 +23,6 @@ class DefaultAuthenticationSuccessHandlerTest extends \PHPUnit_Framework_TestCas protected function setUp() { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - $this->httpUtils = $this->getMock('Symfony\Component\Security\Http\HttpUtils'); $this->request = $this->getMock('Symfony\Component\HttpFoundation\Request'); $this->request->headers = $this->getMock('Symfony\Component\HttpFoundation\HeaderBag'); diff --git a/Tests/Http/EntryPoint/BasicAuthenticationEntryPointTest.php b/Tests/Http/EntryPoint/BasicAuthenticationEntryPointTest.php index b9e289d..5640789 100644 --- a/Tests/Http/EntryPoint/BasicAuthenticationEntryPointTest.php +++ b/Tests/Http/EntryPoint/BasicAuthenticationEntryPointTest.php @@ -16,13 +16,6 @@ use Symfony\Component\Security\Core\Exception\AuthenticationException; class BasicAuthenticationEntryPointTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testStart() { $request = $this->getMock('Symfony\Component\HttpFoundation\Request'); diff --git a/Tests/Http/EntryPoint/DigestAuthenticationEntryPointTest.php b/Tests/Http/EntryPoint/DigestAuthenticationEntryPointTest.php index 8dfd618..5c6eccc 100644 --- a/Tests/Http/EntryPoint/DigestAuthenticationEntryPointTest.php +++ b/Tests/Http/EntryPoint/DigestAuthenticationEntryPointTest.php @@ -17,13 +17,6 @@ use Symfony\Component\Security\Core\Exception\NonceExpiredException; class DigestAuthenticationEntryPointTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testStart() { $request = $this->getMock('Symfony\Component\HttpFoundation\Request'); diff --git a/Tests/Http/EntryPoint/FormAuthenticationEntryPointTest.php b/Tests/Http/EntryPoint/FormAuthenticationEntryPointTest.php index cbec1bd..097912d 100644 --- a/Tests/Http/EntryPoint/FormAuthenticationEntryPointTest.php +++ b/Tests/Http/EntryPoint/FormAuthenticationEntryPointTest.php @@ -16,17 +16,6 @@ use Symfony\Component\HttpKernel\HttpKernelInterface; class FormAuthenticationEntryPointTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpKernel\HttpKernel')) { - $this->markTestSkipped('The "HttpKernel" component is not available'); - } - } - public function testStart() { $request = $this->getMock('Symfony\Component\HttpFoundation\Request', array(), array(), '', false, false); diff --git a/Tests/Http/EntryPoint/RetryAuthenticationEntryPointTest.php b/Tests/Http/EntryPoint/RetryAuthenticationEntryPointTest.php index 91de1ca..1d918ac 100644 --- a/Tests/Http/EntryPoint/RetryAuthenticationEntryPointTest.php +++ b/Tests/Http/EntryPoint/RetryAuthenticationEntryPointTest.php @@ -16,13 +16,6 @@ use Symfony\Component\HttpFoundation\Request; class RetryAuthenticationEntryPointTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - /** * @dataProvider dataForStart */ diff --git a/Tests/Http/Firewall/AbstractPreAuthenticatedListenerTest.php b/Tests/Http/Firewall/AbstractPreAuthenticatedListenerTest.php index 76721ec..e57514b 100644 --- a/Tests/Http/Firewall/AbstractPreAuthenticatedListenerTest.php +++ b/Tests/Http/Firewall/AbstractPreAuthenticatedListenerTest.php @@ -18,21 +18,6 @@ use Symfony\Component\Security\Core\Exception\AuthenticationException; class AbstractPreAuthenticatedListenerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\EventDispatcher\EventDispatcher')) { - $this->markTestSkipped('The "EventDispatcher" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpKernel\HttpKernel')) { - $this->markTestSkipped('The "HttpKernel" component is not available'); - } - } - public function testHandleWithValidValues() { $userCredentials = array('TheUser', 'TheCredentials'); diff --git a/Tests/Http/Firewall/AccessListenerTest.php b/Tests/Http/Firewall/AccessListenerTest.php index 53ab350..961c792 100644 --- a/Tests/Http/Firewall/AccessListenerTest.php +++ b/Tests/Http/Firewall/AccessListenerTest.php @@ -15,21 +15,6 @@ use Symfony\Component\Security\Http\Firewall\AccessListener; class AccessListenerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\EventDispatcher\EventDispatcher')) { - $this->markTestSkipped('The "EventDispatcher" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpKernel\HttpKernel')) { - $this->markTestSkipped('The "HttpKernel" component is not available'); - } - } - /** * @expectedException \Symfony\Component\Security\Core\Exception\AccessDeniedException */ diff --git a/Tests/Http/Firewall/AnonymousAuthenticationListenerTest.php b/Tests/Http/Firewall/AnonymousAuthenticationListenerTest.php index 73ee821..0fd43ec 100644 --- a/Tests/Http/Firewall/AnonymousAuthenticationListenerTest.php +++ b/Tests/Http/Firewall/AnonymousAuthenticationListenerTest.php @@ -15,13 +15,6 @@ use Symfony\Component\Security\Http\Firewall\AnonymousAuthenticationListener; class AnonymousAuthenticationListenerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\EventDispatcher\EventDispatcher')) { - $this->markTestSkipped('The "EventDispatcher" component is not available'); - } - } - public function testHandleWithContextHavingAToken() { $context = $this->getMock('Symfony\Component\Security\Core\SecurityContextInterface'); diff --git a/Tests/Http/Firewall/BasicAuthenticationListenerTest.php b/Tests/Http/Firewall/BasicAuthenticationListenerTest.php index 7616149..b523598 100644 --- a/Tests/Http/Firewall/BasicAuthenticationListenerTest.php +++ b/Tests/Http/Firewall/BasicAuthenticationListenerTest.php @@ -20,21 +20,6 @@ use Symfony\Component\Security\Core\Authentication\AuthenticationProviderManager class BasicAuthenticationListenerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\EventDispatcher\EventDispatcher')) { - $this->markTestSkipped('The "EventDispatcher" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpKernel\HttpKernel')) { - $this->markTestSkipped('The "HttpKernel" component is not available'); - } - } - public function testHandleWithValidUsernameAndPasswordServerParameters() { $request = new Request(array(), array(), array(), array(), array(), array( diff --git a/Tests/Http/Firewall/ChannelListenerTest.php b/Tests/Http/Firewall/ChannelListenerTest.php index 17bf0a0..2005a2b 100644 --- a/Tests/Http/Firewall/ChannelListenerTest.php +++ b/Tests/Http/Firewall/ChannelListenerTest.php @@ -17,21 +17,6 @@ use Symfony\Component\HttpFoundation\Response; class ChannelListenerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\EventDispatcher\EventDispatcher')) { - $this->markTestSkipped('The "EventDispatcher" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpKernel\HttpKernel')) { - $this->markTestSkipped('The "HttpKernel" component is not available'); - } - } - public function testHandleWithNotSecuredRequestAndHttpChannel() { $request = $this->getMock('Symfony\Component\HttpFoundation\Request', array(), array(), '', false, false); diff --git a/Tests/Http/Firewall/ContextListenerTest.php b/Tests/Http/Firewall/ContextListenerTest.php index 336c333..68af9a7 100644 --- a/Tests/Http/Firewall/ContextListenerTest.php +++ b/Tests/Http/Firewall/ContextListenerTest.php @@ -26,18 +26,6 @@ class ContextListenerTest extends \PHPUnit_Framework_TestCase { protected function setUp() { - if (!class_exists('Symfony\Component\EventDispatcher\EventDispatcher')) { - $this->markTestSkipped('The "EventDispatcher" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpKernel\HttpKernel')) { - $this->markTestSkipped('The "HttpKernel" component is not available'); - } - $this->securityContext = new SecurityContext( $this->getMock('Symfony\Component\Security\Core\Authentication\AuthenticationManagerInterface'), $this->getMock('Symfony\Component\Security\Core\Authorization\AccessDecisionManagerInterface') @@ -201,8 +189,8 @@ class ContextListenerTest extends \PHPUnit_Framework_TestCase $listener = new ContextListener($context, array(), 'key123', null, $dispatcher); $event->expects($this->any()) - ->method('getRequestType') - ->will($this->returnValue(HttpKernelInterface::MASTER_REQUEST)); + ->method('isMasterRequest') + ->will($this->returnValue(true)); $event->expects($this->any()) ->method('getRequest') ->will($this->returnValue($this->getMock('Symfony\Component\HttpFoundation\Request'))); diff --git a/Tests/Http/Firewall/LogoutListenerTest.php b/Tests/Http/Firewall/LogoutListenerTest.php index ba94b6e..2c26678 100644 --- a/Tests/Http/Firewall/LogoutListenerTest.php +++ b/Tests/Http/Firewall/LogoutListenerTest.php @@ -17,25 +17,6 @@ use Symfony\Component\Security\Http\Firewall\LogoutListener; class LogoutListenerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\Form\Form')) { - $this->markTestSkipped('The "Form" component is not available'); - } - - if (!class_exists('Symfony\Component\EventDispatcher\EventDispatcher')) { - $this->markTestSkipped('The "EventDispatcher" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpKernel\HttpKernel')) { - $this->markTestSkipped('The "HttpKernel" component is not available'); - } - } - public function testHandleUnmatchedPath() { list($listener, $context, $httpUtils, $options) = $this->getListener(); diff --git a/Tests/Http/Firewall/RememberMeListenerTest.php b/Tests/Http/Firewall/RememberMeListenerTest.php index 8ad4c55..922f99b 100644 --- a/Tests/Http/Firewall/RememberMeListenerTest.php +++ b/Tests/Http/Firewall/RememberMeListenerTest.php @@ -17,21 +17,6 @@ use Symfony\Component\HttpFoundation\Request; class RememberMeListenerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\EventDispatcher\EventDispatcher')) { - $this->markTestSkipped('The "EventDispatcher" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpKernel\HttpKernel')) { - $this->markTestSkipped('The "HttpKernel" component is not available'); - } - } - public function testOnCoreSecurityDoesNotTryToPopulateNonEmptySecurityContext() { list($listener, $context, $service,,) = $this->getListener(); diff --git a/Tests/Http/Firewall/SwitchUserListenerTest.php b/Tests/Http/Firewall/SwitchUserListenerTest.php index f8bb9f6..feb10b8 100644 --- a/Tests/Http/Firewall/SwitchUserListenerTest.php +++ b/Tests/Http/Firewall/SwitchUserListenerTest.php @@ -29,19 +29,12 @@ class SwitchUserListenerTest extends \PHPUnit_Framework_TestCase protected function setUp() { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpKernel\HttpKernel')) { - $this->markTestSkipped('The "HttpKernel" component is not available'); - } - $this->securityContext = $this->getMock('Symfony\Component\Security\Core\SecurityContextInterface'); $this->userProvider = $this->getMock('Symfony\Component\Security\Core\User\UserProviderInterface'); $this->userChecker = $this->getMock('Symfony\Component\Security\Core\User\UserCheckerInterface'); $this->accessDecisionManager = $this->getMock('Symfony\Component\Security\Core\Authorization\AccessDecisionManagerInterface'); $this->request = $this->getMock('Symfony\Component\HttpFoundation\Request'); + $this->request->query = $this->getMock('Symfony\Component\HttpFoundation\ParameterBag'); $this->request->server = $this->getMock('Symfony\Component\HttpFoundation\ServerBag'); $this->event = $this->getEvent($this->request); } @@ -59,7 +52,7 @@ class SwitchUserListenerTest extends \PHPUnit_Framework_TestCase { $this->request->expects($this->any())->method('get')->with('_switch_user')->will($this->returnValue(null)); - $this->event->expects($this->never())->method('setResopnse'); + $this->event->expects($this->never())->method('setResponse'); $this->securityContext->expects($this->never())->method('setToken'); $listener = new SwitchUserListener($this->securityContext, $this->userProvider, $this->userChecker, 'provider123', $this->accessDecisionManager); @@ -94,6 +87,8 @@ class SwitchUserListenerTest extends \PHPUnit_Framework_TestCase $this->request->expects($this->any())->method('get')->with('_switch_user')->will($this->returnValue('_exit')); $this->request->expects($this->any())->method('getUri')->will($this->returnValue('/')); + $this->request->query->expects($this->once())->method('remove','_switch_user'); + $this->request->query->expects($this->any())->method('all')->will($this->returnValue(array())); $this->request->server->expects($this->once())->method('set')->with('QUERY_STRING', ''); $this->securityContext->expects($this->once()) @@ -131,6 +126,9 @@ class SwitchUserListenerTest extends \PHPUnit_Framework_TestCase $this->securityContext->expects($this->any())->method('getToken')->will($this->returnValue($token)); $this->request->expects($this->any())->method('get')->with('_switch_user')->will($this->returnValue('kuba')); + $this->request->query->expects($this->once())->method('remove','_switch_user'); + $this->request->query->expects($this->any())->method('all')->will($this->returnValue(array())); + $this->request->expects($this->any())->method('getUri')->will($this->returnValue('/')); $this->request->server->expects($this->once())->method('set')->with('QUERY_STRING', ''); @@ -150,6 +148,35 @@ class SwitchUserListenerTest extends \PHPUnit_Framework_TestCase $listener->handle($this->event); } + public function testSwitchUserKeepsOtherQueryStringParameters() + { + $token = $this->getToken(array($this->getMock('Symfony\Component\Security\Core\Role\RoleInterface'))); + $user = $this->getMock('Symfony\Component\Security\Core\User\UserInterface'); + $user->expects($this->any())->method('getRoles')->will($this->returnValue(array())); + + $this->securityContext->expects($this->any())->method('getToken')->will($this->returnValue($token)); + $this->request->expects($this->any())->method('get')->with('_switch_user')->will($this->returnValue('kuba')); + $this->request->query->expects($this->once())->method('remove','_switch_user'); + $this->request->query->expects($this->any())->method('all')->will($this->returnValue(array('page'=>3,'section'=>2))); + $this->request->expects($this->any())->method('getUri')->will($this->returnValue('/')); + $this->request->server->expects($this->once())->method('set')->with('QUERY_STRING', 'page=3§ion=2'); + + $this->accessDecisionManager->expects($this->once()) + ->method('decide')->with($token, array('ROLE_ALLOWED_TO_SWITCH')) + ->will($this->returnValue(true)); + + $this->userProvider->expects($this->once()) + ->method('loadUserByUsername')->with('kuba') + ->will($this->returnValue($user)); + $this->userChecker->expects($this->once()) + ->method('checkPostAuth')->with($user); + $this->securityContext->expects($this->once()) + ->method('setToken')->with($this->isInstanceOf('Symfony\Component\Security\Core\Authentication\Token\UsernamePasswordToken')); + + $listener = new SwitchUserListener($this->securityContext, $this->userProvider, $this->userChecker, 'provider123', $this->accessDecisionManager); + $listener->handle($this->event); + } + private function getEvent($request) { $event = $this->getMockBuilder('Symfony\Component\HttpKernel\Event\GetResponseEvent') diff --git a/Tests/Http/Firewall/X509AuthenticationListenerTest.php b/Tests/Http/Firewall/X509AuthenticationListenerTest.php index 81ac0f7..77e5e6a 100644 --- a/Tests/Http/Firewall/X509AuthenticationListenerTest.php +++ b/Tests/Http/Firewall/X509AuthenticationListenerTest.php @@ -16,13 +16,6 @@ use Symfony\Component\Security\Http\Firewall\X509AuthenticationListener; class X509AuthenticationListenerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - /** * @dataProvider dataProviderGetPreAuthenticatedData */ diff --git a/Tests/Http/FirewallMapTest.php b/Tests/Http/FirewallMapTest.php index c7f13e1..5d3a72a 100644 --- a/Tests/Http/FirewallMapTest.php +++ b/Tests/Http/FirewallMapTest.php @@ -16,17 +16,6 @@ use Symfony\Component\HttpFoundation\Request; class FirewallMapTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\EventDispatcher\EventDispatcher')) { - $this->markTestSkipped('The "EventDispatcher" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testGetListeners() { $map = new FirewallMap(); diff --git a/Tests/Http/FirewallTest.php b/Tests/Http/FirewallTest.php index 0c1d82c..1ea7e57 100644 --- a/Tests/Http/FirewallTest.php +++ b/Tests/Http/FirewallTest.php @@ -17,21 +17,6 @@ use Symfony\Component\HttpKernel\HttpKernelInterface; class FirewallTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\EventDispatcher\EventDispatcher')) { - $this->markTestSkipped('The "EventDispatcher" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!class_exists('Symfony\Component\HttpKernel\HttpKernel')) { - $this->markTestSkipped('The "HttpKernel" component is not available'); - } - } - public function testOnKernelRequestRegistersExceptionListener() { $dispatcher = $this->getMock('Symfony\Component\EventDispatcher\EventDispatcherInterface'); diff --git a/Tests/Http/HttpUtilsTest.php b/Tests/Http/HttpUtilsTest.php index db1aa4b..07a3ee9 100644 --- a/Tests/Http/HttpUtilsTest.php +++ b/Tests/Http/HttpUtilsTest.php @@ -19,17 +19,6 @@ use Symfony\Component\Security\Http\HttpUtils; class HttpUtilsTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - - if (!class_exists('Symfony\Component\Routing\Router')) { - $this->markTestSkipped('The "Routing" component is not available'); - } - } - public function testCreateRedirectResponseWithPath() { $utils = new HttpUtils($this->getUrlGenerator()); diff --git a/Tests/Http/Logout/CookieClearingLogoutHandlerTest.php b/Tests/Http/Logout/CookieClearingLogoutHandlerTest.php index b32a813..c443d8d 100644 --- a/Tests/Http/Logout/CookieClearingLogoutHandlerTest.php +++ b/Tests/Http/Logout/CookieClearingLogoutHandlerTest.php @@ -18,13 +18,6 @@ use Symfony\Component\Security\Http\Logout\CookieClearingLogoutHandler; class CookieClearingLogoutHandlerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testLogout() { $request = new Request(); diff --git a/Tests/Http/Logout/DefaultLogoutSuccessHandlerTest.php b/Tests/Http/Logout/DefaultLogoutSuccessHandlerTest.php index e1b1227..ed65d6b 100644 --- a/Tests/Http/Logout/DefaultLogoutSuccessHandlerTest.php +++ b/Tests/Http/Logout/DefaultLogoutSuccessHandlerTest.php @@ -16,13 +16,6 @@ use Symfony\Component\Security\Http\Logout\DefaultLogoutSuccessHandler; class DefaultLogoutSuccessHandlerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testLogout() { $request = $this->getMock('Symfony\Component\HttpFoundation\Request'); diff --git a/Tests/Http/Logout/SessionLogoutHandlerTest.php b/Tests/Http/Logout/SessionLogoutHandlerTest.php index 8e2dd28..f89a423 100644 --- a/Tests/Http/Logout/SessionLogoutHandlerTest.php +++ b/Tests/Http/Logout/SessionLogoutHandlerTest.php @@ -16,13 +16,6 @@ use Symfony\Component\Security\Http\Logout\SessionLogoutHandler; class SessionLogoutHandlerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testLogout() { $handler = new SessionLogoutHandler(); diff --git a/Tests/Http/RememberMe/AbstractRememberMeServicesTest.php b/Tests/Http/RememberMe/AbstractRememberMeServicesTest.php index 8571686..20ac195 100644 --- a/Tests/Http/RememberMe/AbstractRememberMeServicesTest.php +++ b/Tests/Http/RememberMe/AbstractRememberMeServicesTest.php @@ -17,13 +17,6 @@ use Symfony\Component\HttpFoundation\Response; class AbstractRememberMeServicesTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testGetRememberMeParameter() { $service = $this->getService(null, array('remember_me_parameter' => 'foo')); diff --git a/Tests/Http/RememberMe/PersistentTokenBasedRememberMeServicesTest.php b/Tests/Http/RememberMe/PersistentTokenBasedRememberMeServicesTest.php index 7fc3021..8978725 100644 --- a/Tests/Http/RememberMe/PersistentTokenBasedRememberMeServicesTest.php +++ b/Tests/Http/RememberMe/PersistentTokenBasedRememberMeServicesTest.php @@ -26,13 +26,6 @@ use Symfony\Component\Security\Core\Util\SecureRandom; class PersistentTokenBasedRememberMeServicesTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testAutoLoginReturnsNullWhenNoCookie() { $service = $this->getService(null, array('name' => 'foo')); diff --git a/Tests/Http/RememberMe/ResponseListenerTest.php b/Tests/Http/RememberMe/ResponseListenerTest.php index cbd3f1f..887ec69 100644 --- a/Tests/Http/RememberMe/ResponseListenerTest.php +++ b/Tests/Http/RememberMe/ResponseListenerTest.php @@ -19,13 +19,6 @@ use Symfony\Component\HttpKernel\KernelEvents; class ResponseListenerTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testRememberMeCookieIsSentWithResponse() { $cookie = new Cookie('rememberme'); @@ -41,7 +34,7 @@ class ResponseListenerTest extends \PHPUnit_Framework_TestCase $listener->onKernelResponse($this->getEvent($request, $response)); } - public function testRemmeberMeCookieIsNotSendWithResponse() + public function testRememberMeCookieIsNotSendWithResponse() { $request = $this->getRequest(); diff --git a/Tests/Http/RememberMe/TokenBasedRememberMeServicesTest.php b/Tests/Http/RememberMe/TokenBasedRememberMeServicesTest.php index 6de69f1..7856038 100644 --- a/Tests/Http/RememberMe/TokenBasedRememberMeServicesTest.php +++ b/Tests/Http/RememberMe/TokenBasedRememberMeServicesTest.php @@ -23,13 +23,6 @@ use Symfony\Component\Security\Http\RememberMe\TokenBasedRememberMeServices; class TokenBasedRememberMeServicesTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testAutoLoginReturnsNullWhenNoCookie() { $service = $this->getService(null, array('name' => 'foo')); diff --git a/Tests/Http/Session/SessionAuthenticationStrategyTest.php b/Tests/Http/Session/SessionAuthenticationStrategyTest.php index 43c52b5..6918503 100644 --- a/Tests/Http/Session/SessionAuthenticationStrategyTest.php +++ b/Tests/Http/Session/SessionAuthenticationStrategyTest.php @@ -15,13 +15,6 @@ use Symfony\Component\Security\Http\Session\SessionAuthenticationStrategy; class SessionAuthenticationStrategyTest extends \PHPUnit_Framework_TestCase { - protected function setUp() - { - if (!class_exists('Symfony\Component\HttpFoundation\Request')) { - $this->markTestSkipped('The "HttpFoundation" component is not available'); - } - } - public function testSessionIsNotChanged() { $request = $this->getRequest(); diff --git a/composer.json b/composer.json index 826c58b..fe1299c 100644 --- a/composer.json +++ b/composer.json @@ -18,8 +18,8 @@ "require": { "php": ">=5.3.3", "symfony/event-dispatcher": "~2.1", - "symfony/http-foundation": "~2.1", - "symfony/http-kernel": "~2.1" + "symfony/http-foundation": "~2.4", + "symfony/http-kernel": "~2.4" }, "require-dev": { "symfony/form": "~2.0", @@ -46,7 +46,7 @@ "minimum-stability": "dev", "extra": { "branch-alias": { - "dev-master": "2.3-dev" + "dev-master": "2.4-dev" } } } |