diff options
author | Johannes M. Schmitt <schmittjoh@gmail.com> | 2011-01-26 21:34:11 +0100 |
---|---|---|
committer | Fabien Potencier <fabien.potencier@gmail.com> | 2011-01-26 22:23:20 +0100 |
commit | bebc09870cb0a7720e2c6a8c5c74585e69e8bb24 (patch) | |
tree | 0c399647cdbe504be405017e7cc04c70c53482f2 /Core/Authentication/Provider | |
parent | c85f3d708d2c9b00d73ca1234ccfaf50336d94b1 (diff) | |
download | symfony-security-bebc09870cb0a7720e2c6a8c5c74585e69e8bb24.zip symfony-security-bebc09870cb0a7720e2c6a8c5c74585e69e8bb24.tar.gz symfony-security-bebc09870cb0a7720e2c6a8c5c74585e69e8bb24.tar.bz2 |
namespace changes
Symfony\Component\Security -> Symfony\Component\Security\Core
Symfony\Component\Security\Acl remains unchanged
Symfony\Component\HttpKernel\Security -> Symfony\Component\Security\Http
Diffstat (limited to 'Core/Authentication/Provider')
6 files changed, 429 insertions, 0 deletions
diff --git a/Core/Authentication/Provider/AnonymousAuthenticationProvider.php b/Core/Authentication/Provider/AnonymousAuthenticationProvider.php new file mode 100644 index 0000000..821e17e --- /dev/null +++ b/Core/Authentication/Provider/AnonymousAuthenticationProvider.php @@ -0,0 +1,60 @@ +<?php + +/* + * This file is part of the Symfony package. + * + * (c) Fabien Potencier <fabien.potencier@symfony-project.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\Authentication\Token\TokenInterface; +use Symfony\Component\Security\Core\Exception\BadCredentialsException; +use Symfony\Component\Security\Core\Authentication\Token\AnonymousToken; + +/** + * AnonymousAuthenticationProvider validates AnonymousToken instances. + * + * @author Fabien Potencier <fabien.potencier@symfony-project.com> + */ +class AnonymousAuthenticationProvider implements AuthenticationProviderInterface +{ + protected $key; + + /** + * Constructor. + * + * @param string $key The key shared with the authentication token + */ + public function __construct($key) + { + $this->key = $key; + } + + /** + * {@inheritdoc} + */ + public function authenticate(TokenInterface $token) + { + if (!$this->supports($token)) { + return null; + } + + if ($this->key != $token->getKey()) { + throw new BadCredentialsException('The Token does not contain the expected key.'); + } + + return $token; + } + + /** + * {@inheritdoc} + */ + public function supports(TokenInterface $token) + { + return $token instanceof AnonymousToken; + } +} diff --git a/Core/Authentication/Provider/AuthenticationProviderInterface.php b/Core/Authentication/Provider/AuthenticationProviderInterface.php new file mode 100644 index 0000000..89d5ed5 --- /dev/null +++ b/Core/Authentication/Provider/AuthenticationProviderInterface.php @@ -0,0 +1,35 @@ +<?php + +/* + * This file is part of the Symfony package. + * + * (c) Fabien Potencier <fabien.potencier@symfony-project.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\Authentication\Token\TokenInterface; +use Symfony\Component\Security\Core\Authentication\AuthenticationManagerInterface; + +/** + * AuthenticationProviderInterface is the interface for for all authentication + * providers. + * + * Concrete implementations processes specific Token instances. + * + * @author Fabien Potencier <fabien.potencier@symfony-project.com> + */ +interface AuthenticationProviderInterface extends AuthenticationManagerInterface +{ + /** + * Checks whether this provider supports the given token. + * + * @param TokenInterface $token A TokenInterface instance + * + * @return Boolean true if the implementation supports the Token, false otherwise + */ + function supports(TokenInterface $token); +} diff --git a/Core/Authentication/Provider/DaoAuthenticationProvider.php b/Core/Authentication/Provider/DaoAuthenticationProvider.php new file mode 100644 index 0000000..398f586 --- /dev/null +++ b/Core/Authentication/Provider/DaoAuthenticationProvider.php @@ -0,0 +1,95 @@ +<?php + +/* + * This file is part of the Symfony package. + * + * (c) Fabien Potencier <fabien.potencier@symfony-project.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\Authentication\Token\TokenInterface; +use Symfony\Component\Security\Core\Encoder\EncoderFactoryInterface; +use Symfony\Component\Security\Core\User\UserProviderInterface; +use Symfony\Component\Security\Core\User\AccountCheckerInterface; +use Symfony\Component\Security\Core\User\AccountInterface; +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\UsernamePasswordToken; + +/** + * DaoAuthenticationProvider uses a UserProviderInterface to retrieve the user + * for a UsernamePasswordToken. + * + * @author Fabien Potencier <fabien.potencier@symfony-project.com> + */ +class DaoAuthenticationProvider extends UserAuthenticationProvider +{ + protected $encoderFactory; + protected $userProvider; + + /** + * Constructor. + * + * @param UserProviderInterface $userProvider A UserProviderInterface instance + * @param AccountCheckerInterface $accountChecker An AccountCheckerInterface instance + * @param EncoderFactoryInterface $encoderFactory A EncoderFactoryInterface instance + */ + public function __construct(UserProviderInterface $userProvider, AccountCheckerInterface $accountChecker, $providerKey, EncoderFactoryInterface $encoderFactory, $hideUserNotFoundExceptions = true) + { + parent::__construct($accountChecker, $providerKey, $hideUserNotFoundExceptions); + + $this->encoderFactory = $encoderFactory; + $this->userProvider = $userProvider; + } + + /** + * {@inheritdoc} + */ + protected function checkAuthentication(AccountInterface $account, UsernamePasswordToken $token) + { + $user = $token->getUser(); + if ($user instanceof AccountInterface) { + if ($account->getPassword() !== $user->getPassword()) { + throw new BadCredentialsException('The credentials were changed from another session.'); + } + } else { + if (!$presentedPassword = (string) $token->getCredentials()) { + throw new BadCredentialsException('Bad credentials'); + } + + if (!$this->encoderFactory->getEncoder($account)->isPasswordValid($account->getPassword(), $presentedPassword, $account->getSalt())) { + throw new BadCredentialsException('Bad credentials'); + } + } + } + + /** + * {@inheritdoc} + */ + protected function retrieveUser($username, UsernamePasswordToken $token) + { + $user = $token->getUser(); + if ($user instanceof AccountInterface) { + return $user; + } + + try { + $user = $this->userProvider->loadUserByUsername($username); + + if (!$user instanceof AccountInterface) { + throw new AuthenticationServiceException('The user provider must return an AccountInterface object.'); + } + + return $user; + } catch (UsernameNotFoundException $notFound) { + throw $notFound; + } catch (\Exception $repositoryProblem) { + throw new AuthenticationServiceException($repositoryProblem->getMessage(), $token, 0, $repositoryProblem); + } + } +} diff --git a/Core/Authentication/Provider/PreAuthenticatedAuthenticationProvider.php b/Core/Authentication/Provider/PreAuthenticatedAuthenticationProvider.php new file mode 100644 index 0000000..7fda9d4 --- /dev/null +++ b/Core/Authentication/Provider/PreAuthenticatedAuthenticationProvider.php @@ -0,0 +1,81 @@ +<?php + +/* + * This file is part of the Symfony package. + * + * (c) Fabien Potencier <fabien.potencier@symfony-project.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\User\AccountInterface; +use Symfony\Component\Security\Core\User\UserProviderInterface; +use Symfony\Component\Security\Core\User\AccountCheckerInterface; +use Symfony\Component\Security\Core\Exception\BadCredentialsException; +use Symfony\Component\Security\Core\Authentication\Token\PreAuthenticatedToken; +use Symfony\Component\Security\Core\Authentication\Token\TokenInterface; + +/** + * Processes a pre-authenticated authentication request. + * + * This authentication provider will not perform any checks on authentication + * requests, as they should already be pre-authenticated. However, the + * UserProviderInterface implementation may still throw a + * UsernameNotFoundException, for example. + * + * @author Fabien Potencier <fabien.potencier@symfony-project.com> + */ +class PreAuthenticatedAuthenticationProvider implements AuthenticationProviderInterface +{ + protected $userProvider; + protected $accountChecker; + protected $providerKey; + + /** + * Constructor. + * + * @param UserProviderInterface $userProvider A UserProviderInterface instance + * @param AccountCheckerInterface $accountChecker An AccountCheckerInterface instance + */ + public function __construct(UserProviderInterface $userProvider, AccountCheckerInterface $accountChecker, $providerKey) + { + $this->userProvider = $userProvider; + $this->accountChecker = $accountChecker; + $this->providerKey = $providerKey; + } + + /** + * {@inheritdoc} + */ + public function authenticate(TokenInterface $token) + { + if (!$this->supports($token)) { + return null; + } + + if (!$user = $token->getUser()) { + throw new BadCredentialsException('No pre-authenticated principal found in request.'); + } +/* + if (null === $token->getCredentials()) { + throw new BadCredentialsException('No pre-authenticated credentials found in request.'); + } +*/ + $user = $this->userProvider->loadUserByUsername($user); + + $this->accountChecker->checkPostAuth($user); + + return new PreAuthenticatedToken($user, $token->getCredentials(), $user->getRoles()); + } + + /** + * {@inheritdoc} + */ + public function supports(TokenInterface $token) + { + return $token instanceof PreAuthenticatedToken && $this->providerKey === $token->getProviderKey(); + } +} diff --git a/Core/Authentication/Provider/RememberMeAuthenticationProvider.php b/Core/Authentication/Provider/RememberMeAuthenticationProvider.php new file mode 100644 index 0000000..95ee588 --- /dev/null +++ b/Core/Authentication/Provider/RememberMeAuthenticationProvider.php @@ -0,0 +1,45 @@ +<?php +namespace Symfony\Component\Security\Core\Authentication\Provider; + +use Symfony\Component\Security\Core\User\AccountCheckerInterface; +use Symfony\Component\Security\Core\User\AccountInterface; +use Symfony\Component\Security\Core\Authentication\Token\TokenInterface; +use Symfony\Component\Security\Core\Authentication\Token\RememberMeToken; +use Symfony\Component\Security\Core\Exception\BadCredentialsException; + +class RememberMeAuthenticationProvider implements AuthenticationProviderInterface +{ + protected $accountChecker; + protected $key; + protected $providerKey; + + public function __construct(AccountCheckerInterface $accountChecker, $key, $providerKey) + { + $this->accountChecker = $accountChecker; + $this->key = $key; + $this->providerKey = $providerKey; + } + + public function authenticate(TokenInterface $token) + { + if (!$this->supports($token)) { + return; + } + + if ($this->key !== $token->getKey()) { + throw new BadCredentialsException('The presented key does not match.'); + } + + $user = $token->getUser(); + $this->accountChecker->checkPreAuth($user); + $this->accountChecker->checkPostAuth($user); + $token->setAuthenticated(true); + + return $token; + } + + public function supports(TokenInterface $token) + { + return $token instanceof RememberMeToken && $token->getProviderKey() === $this->providerKey; + } +}
\ No newline at end of file diff --git a/Core/Authentication/Provider/UserAuthenticationProvider.php b/Core/Authentication/Provider/UserAuthenticationProvider.php new file mode 100644 index 0000000..6947de3 --- /dev/null +++ b/Core/Authentication/Provider/UserAuthenticationProvider.php @@ -0,0 +1,113 @@ +<?php + +/* + * This file is part of the Symfony package. + * + * (c) Fabien Potencier <fabien.potencier@symfony-project.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\User\AccountInterface; +use Symfony\Component\Security\Core\User\AccountCheckerInterface; +use Symfony\Component\Security\Core\Exception\UsernameNotFoundException; +use Symfony\Component\Security\Core\Exception\AuthenticationException; +use Symfony\Component\Security\Core\Exception\BadCredentialsException; +use Symfony\Component\Security\Core\Exception\AuthenticationServiceException; +use Symfony\Component\Security\Core\Authentication\Token\UsernamePasswordToken; +use Symfony\Component\Security\Core\Authentication\Token\TokenInterface; + +/** + * UserProviderInterface retrieves users for UsernamePasswordToken tokens. + * + * @author Fabien Potencier <fabien.potencier@symfony-project.com> + */ +abstract class UserAuthenticationProvider implements AuthenticationProviderInterface +{ + protected $hideUserNotFoundExceptions; + protected $accountChecker; + protected $providerKey; + + /** + * Constructor. + * + * @param AccountCheckerInterface $accountChecker An AccountCheckerInterface interface + * @param Boolean $hideUserNotFoundExceptions Whether to hide user not found exception or not + */ + public function __construct(AccountCheckerInterface $accountChecker, $providerKey, $hideUserNotFoundExceptions = true) + { + if (empty($providerKey)) { + throw new \InvalidArgumentException('$providerKey must not be empty.'); + } + + $this->accountChecker = $accountChecker; + $this->providerKey = $providerKey; + $this->hideUserNotFoundExceptions = $hideUserNotFoundExceptions; + } + + /** + * {@inheritdoc} + */ + public function authenticate(TokenInterface $token) + { + if (!$this->supports($token)) { + return null; + } + + $username = null === $token->getUser() ? 'NONE_PROVIDED' : (string) $token; + + try { + $user = $this->retrieveUser($username, $token); + + if (!$user instanceof AccountInterface) { + throw new AuthenticationServiceException('retrieveUser() must return an AccountInterface.'); + } + + $this->accountChecker->checkPreAuth($user); + $this->checkAuthentication($user, $token); + $this->accountChecker->checkPostAuth($user); + + return new UsernamePasswordToken($user, $token->getCredentials(), $this->providerKey, $user->getRoles()); + } catch (UsernameNotFoundException $notFound) { + if ($this->hideUserNotFoundExceptions) { + throw new BadCredentialsException('Bad credentials', 0, $notFound); + } + + throw $notFound; + } + } + + /** + * {@inheritdoc} + */ + public function supports(TokenInterface $token) + { + return $token instanceof UsernamePasswordToken && $this->providerKey === $token->getProviderKey(); + } + + /** + * Retrieves the user from an implementation-specific location. + * + * @param string $username The username to retrieve + * @param UsernamePasswordToken $token The Token + * + * @return array The user + * + * @throws AuthenticationException if the credentials could not be validated + */ + abstract protected function retrieveUser($username, UsernamePasswordToken $token); + + /** + * Does additional checks on the user and token (like validating the + * credentials). + * + * @param AccountInterface $account The retrieved AccountInterface instance + * @param UsernamePasswordToken $token The UsernamePasswordToken token to be authenticated + * + * @throws AuthenticationException if the credentials could not be validated + */ + abstract protected function checkAuthentication(AccountInterface $account, UsernamePasswordToken $token); +} |