问题描述
创建用户后,应先登录,然后将guardHandler与身份验证器一起使用,如下所示。
use App\Security\FakeAuthenticator;
use Symfony\Component\Security\Guard\GuardAuthenticatorHandler;
$response = $guardHandler->authenticateUserAndHandleSuccess(
$user,// the User object you just created
$request,$authenticator,// authenticator whose onAuthenticationSuccess you want to use
'main' // the name of your firewall in security.yaml
);
但是,身份验证器是一团糟,它只是为一种方法onAuthenticationSuccess
创建的。
use Symfony\Component\Security\Guard\AbstractGuardAuthenticator;
class FakeAuthenticator extends AbstractGuardAuthenticator
{
public function supports(Request $request)
{
return false;
}
public function getCredentials(Request $request)
{
throw new \RuntimeException('Unreachable code');
}
public function getUser($credentials,UserProviderInterface $userProvider)
{
throw new \RuntimeException('Unreachable code');
}
public function checkCredentials($credentials,UserInterface $user)
{
throw new \RuntimeException('Unreachable code');
}
public function onAuthenticationSuccess(Request $request,TokenInterface $token,$providerKey)
{
return null;
}
public function onAuthenticationFailure(Request $request,AuthenticationException $exception)
{
throw new \RuntimeException('Unreachable code');
}
public function start(Request $request,AuthenticationException $authException = null)
{
throw new \RuntimeException('Unreachable code');
}
public function supportsRememberMe()
{
return true;
}
}
由于方法handleAuthenticationSuccess
需要一个实现AuthenticatorInterface
的类,因此必须实现许多方法。
该代码可以正常工作,并且用户已登录,但感觉不是最干净的解决方案,还有另一种方法可以登录用户吗?
项目中使用了FosUserBundle,以下内容确实起作用,但是我不确定是否支持loginManager上的调用方法,我在文档中找不到任何内容,并且我不希望我的代码依赖于功能可能会发生变化。
\FOS\UserBundle\Security\LoginManagerInterface::logInUser('main',$user,$response);
解决方法
我决定使用loginManager
及其公共方法logInUser
,这是最干净的解决方案,而无需为单个方法创建额外的类。
use FOS\UserBundle\Security\LoginManager;
...
public function createUserInControllerAction(LoginManagerInterface $loginManager): Response
{
$user = new User(); // create user however you like
$loginManager->logInUser('main',$user,$response);
return $this->json(['success']);
}