[英]Symfony guard throws AuthenticationException but user loaded successfully
I want to implement form login with Symfony/Security to my app.我想使用 Symfony/Security 实现表单登录到我的应用程序。 I configured everything but it still doesn't work properly.我配置了所有内容,但它仍然无法正常工作。
This is my security.yaml :这是我的security.yaml :
security:
providers:
sablon_users:
entity:
class: App\Entity\User
property: email
firewalls:
dev:
pattern: ^/(_(profiler|wdt)|css|images|js)/
security: false
admin_login:
anonymous: true
pattern: ^/admin/auth
form_login:
login_path: security_login
check_path: security_login
csrf_token_generator: security.csrf.token_manager
default_target_path: /admin
admin:
pattern: ^/admin
guard:
authenticators:
- App\Security\LoginAuthenticator
provider: sablon_users
logout:
path: admin_logout
target: security_login
main:
pattern: ^/
anonymous: true
# activate different ways to authenticate
# http_basic: true
# https://symfony.com/doc/current/security.html#a-configuring-how-your-users-will-authenticate
# form_login: true
# https://symfony.com/doc/current/security/form_login_setup.html
# Easy way to control access for large sections of your site
# Note: Only the *first* access control that matches will be used
access_control:
- { path: ^/admin/auth/, roles: IS_AUTHENTICATED_ANONYMOUSLY }
- { path: ^/admin, roles: IS_AUTHENTICATED_FULLY }
encoders:
App\Entity\User:
algorithm: bcrypt
cost: 12
my routes.yaml :我的routes.yaml :
admin_logout:
path: /admin/auth/logout
admin:
type: annotation
resource: ../src/Controller/Admin
prefix: /admin
site:
type: annotation
resource: ../src/Controller/Site
LoginAuthenticator.php :登录验证器.php :
class LoginAuthenticator extends AbstractFormLoginAuthenticator
{
/**
* @var EntityManagerInterface
*/
private $em;
/**
* @var RouterInterface
*/
private $router;
/**
* @var UserPasswordEncoderInterface
*/
private $encoder;
/**
* @var CsrfTokenManagerInterface
*/
private $csrfTokenManager;
/**
* @var TokenStorageInterface
*/
private $tokenStorage;
/**
* LoginAuthenticator constructor.
*
* @param EntityManagerInterface $em
* @param CsrfTokenManagerInterface $csrfTokenManager
* @param RouterInterface $router
* @param TokenStorageInterface $tokenStorage
* @param UserPasswordEncoderInterface $encoder
*/
public function __construct(
EntityManagerInterface $em,
CsrfTokenManagerInterface $csrfTokenManager,
RouterInterface $router,
TokenStorageInterface $tokenStorage,
UserPasswordEncoderInterface $encoder
)
{
$this->em = $em;
$this->csrfTokenManager = $csrfTokenManager;
$this->router = $router;
$this->tokenStorage = $tokenStorage;
$this->encoder = $encoder;
}
/**
* @param Request $request
* @return bool
*/
/**
* @return mixed
*/
public function getCurrentUser()
{
$token = $this->tokenStorage->getToken();
return $token->getUser();
}
/**
* Does the authenticator support the given Request?
*
* If this returns false, the authenticator will be skipped.
*
* @param Request $request
*
* @return bool
*/
public function supports(Request $request)
{
$isLoginSubmitRequest = $request->getPathInfo() === 'admin/auth/login' && $request->isMethod('POST');
if(!$isLoginSubmitRequest){
return false;
}
return true;
}
/**
* @param Request $request
*
* @return mixed Any non-null value
*
* @throws \UnexpectedValueException If null is returned
*/
public function getCredentials(Request $request)
{
$credentials = [
'email' => $request->request->get('email'),
'password' => $request->request->get('password'),
'csrf_token' => $request->request->get('_csrf_token'),
];
$request->getSession()->set(
Security::LAST_USERNAME,
$credentials['email']
);
return $credentials;
}
/**
* @param mixed $credentials
* @param UserProviderInterface $userProvider
* @return User|null|object|UserInterface
*/
public function getUser($credentials, UserProviderInterface $userProvider)
{
$token = new CsrfToken('authenticate', $credentials['csrf_token']);
if (!$this->csrfTokenManager->isTokenValid($token)) {
throw new InvalidCsrfTokenException();
}
$user = $this->em->getRepository(User::class)->findOneBy(['email' => $credentials['email']]);
if (!$user) {
// fail authentication with a custom error
throw new Exception('Email could not be found.');
}
return $user;
}
/**
* @param mixed $credentials
* @param UserInterface $user
*
* @return bool
*
* @throws AuthenticationException
*/
public function checkCredentials($credentials, UserInterface $user)
{
$password = $credentials['password'];
return $this->encoder->isPasswordValid($user,$password);
}
/**
*
* @param Request $request
* @param AuthenticationException $exception
*
* @return Response|null
*/
public function onAuthenticationFailure(Request $request, AuthenticationException $exception)
{
$request->getSession()->set(Security::AUTHENTICATION_ERROR, $exception);
return new RedirectResponse($this->router->generate('security_login'));
}
/**
* @param Request $request
* @param TokenInterface $token
* @param string $providerKey The provider (i.e. firewall) key
*
* @return Response|null
*/
public function onAuthenticationSuccess(Request $request, TokenInterface $token, $providerKey)
{
return new RedirectResponse($this->router->generate('app_homepage'));
}
/**
* @return bool
*/
public function supportsRememberMe()
{
return false;
}
/**
* Return the URL to the login page.
*
* @return string
*/
protected function getLoginUrl()
{
return $this->router->generate('security_login');
}
When i try to login with correct credentials.当我尝试使用正确的凭据登录时。 It loads User and even show the username on the _profiler as authenticated (Token class: UsernamePasswordToken).它加载用户,甚至在 _profiler 上将用户名显示为已验证(令牌类:UsernamePasswordToken)。 It shows the corresponding roles for the user.它显示用户的相应角色。
However when i try to navigate '/admin' area, it redirects me to login page.但是,当我尝试导航“/admin”区域时,它会将我重定向到登录页面。 It doesn't show any error in page or console.它不会在页面或控制台中显示任何错误。
My dev.log shows the flow though:我的 dev.log 显示了流程:
I had the same problem: messages saying 'Guard authenticator does not support the request.', and in my case the issue was that I had symfony using https instead of http using a redirect in .htaccess.我遇到了同样的问题:消息说“保护身份验证器不支持请求。”,在我的情况下,问题是我使用 https 而不是 http 使用 symfony 使用 .htaccess 中的重定向。
In my case the solution was as simple as to go to the https webpage: - https://localhost/login在我的情况下,解决方案就像转到 https 网页一样简单: - https://localhost/login
once there the login was successful.一旦那里登录成功。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.