首页 > 解决方案 > Symfony 5:使用 make:auth Authenticator 的非持久用户

问题描述

都在标题中。当我登录时,它是成功的,我可以通过控制器中的 $this->getUser() 获取用户以响应登录路由,但是当我刷新页面/站点时,$this->getUser() 回到“null” “ 价值。

基本安全.yaml:

security:

    enable_authenticator_manager: true
    password_hashers:
        Symfony\Component\Security\Core\User\PasswordAuthenticatedUserInterface: 'auto'
        App\Entity\User:
            algorithm: auto

    providers:
        app_user_provider:
            entity:
                class: App\Entity\User
                property: username
    firewalls:
        dev:
            pattern: ^/(_(profiler|wdt)|css|images|js)/
            security: false
        main:
            lazy: true
            provider: app_user_provider
            custom_authenticator:
                - App\Security\Authenticator
            logout:
                path: app_logout
               
    access_control:
        # - { path: ^/admin, roles: ROLE_ADMIN }
        # - { path: ^/profile, roles: ROLE_USER }

API 上下文中的身份验证器(这就是 authenticationSuccess 返回 null 的原因):

<?php

namespace App\Security;

use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\Routing\Generator\UrlGeneratorInterface;
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
use Symfony\Component\Security\Core\Security;
use Symfony\Component\Security\Http\Authenticator\AbstractLoginFormAuthenticator;
use Symfony\Component\Security\Http\Authenticator\Passport\Badge\UserBadge;
use Symfony\Component\Security\Http\Authenticator\Passport\Credentials\PasswordCredentials;
use Symfony\Component\Security\Http\Authenticator\Passport\Passport;
use Symfony\Component\Security\Http\Authenticator\Passport\PassportInterface;
use Symfony\Component\Security\Http\Util\TargetPathTrait;

class Authenticator extends AbstractLoginFormAuthenticator
{
use TargetPathTrait;

public const LOGIN_ROUTE = 'app_login';

private UrlGeneratorInterface $urlGenerator;

public function __construct(UrlGeneratorInterface $urlGenerator)
{
    $this->urlGenerator = $urlGenerator;
}

public function authenticate(Request $request): PassportInterface
{
    $parameters = json_decode($request->getContent(), true);

    return new Passport(
        new UserBadge($parameters['username']),
        new PasswordCredentials($parameters['password'])
    );
}

public function onAuthenticationSuccess(Request $request, TokenInterface $token, string $firewallName): ?Response
{
    return null;
}

protected function getLoginUrl(Request $request): string
{
    return $this->urlGenerator->generate(self::LOGIN_ROUTE);
}

}

Controller中的登录路径:

/**
 * @Route("/login", name="app_login")
 */
public function login(AuthenticationUtils $authenticationUtils): Response
{
    $error = $authenticationUtils->getLastAuthenticationError();
    if($error) { 
        return $this->json(['error' => $error->getMessage()]);
    } else {
        return $this->json($this->getUser());
    }
}

来自 FRONTEND 的带有凭据的角度请求:

this.http.post("http://localhost:8000/login", this.myForm.value).subscribe(
  (res : any) => (
    this.snackBar.open(res.error || "You are logged", "Close"), 
    localStorage.setItem("username", res.username || undefined), 
    localStorage.setItem("email", res.email || undefined)
  )
);

标签: symfonysymfony5

解决方案


推荐阅读