You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Symfony 5.8.14登录异常:用户存在却提示不存在

Symfony 5.8.14登录提示"Invalid Credentials"但用户实际存在的问题解决

在Symfony 5.8.14项目中登录用户时,页面显示“Invalid Credentials”错误,日志提示用户不存在,但PHPMyAdmin中确认该用户确实存在。尝试修改security.yaml时提示“Invalid Parameters”,重建项目后问题依旧。

SecurityController代码

<?php

namespace App\Controller;

use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\Routing\Attribute\Route;
use Symfony\Component\Security\Http\Authentication\AuthenticationUtils;

class SecurityController extends AbstractController
{
    #[Route(path: '/login', name: 'app_login')]
    public function login(AuthenticationUtils $authenticationUtils): Response
    {
        // get the login error if there is one
        $error = $authenticationUtils->getLastAuthenticationError();

        // last username entered by the user
        $lastUsername = $authenticationUtils->getLastUsername();

        return $this->render('security/login.html.twig', [
            'last_username' => $lastUsername,
            'error' => $error,
        ]);
    }

    #[Route(path: '/logout', name: 'app_logout')]
    public function logout(): void
    {
        throw new \LogicException('This method can be blank - it will be intercepted by the logout key on your firewall.');
    }
}

登录页面模板

{% extends 'base.html.twig' %}

{% block title %}Log in!{% endblock %}

{% block body %}
    <div class="flex justify-center items-center min-h-screen bg-gray-100">
        <div class="w-full max-w-md p-8 bg-white rounded-lg shadow-lg">
            {% if error %}
                <div class="mb-4 p-4 bg-red-50 border border-red-200 text-red-600 rounded-md">
                    {{ error.messageKey|trans(error.messageData, 'security') }}
                </div>
            {% endif %}

            {% if app.user %}
                <div class="mb-4 text-gray-600">
                    You are logged in as <span class="font-semibold">{{ app.user.userIdentifier }}</span>,
                    <a href="{{ path('app_logout') }}" class="text-indigo-600 hover:text-indigo-800">Logout</a>
                </div>
            {% endif %}

            <h1 class="text-2xl font-bold text-gray-900 mb-6 text-center">Please Sign In</h1>

            <form method="post" class="space-y-6 relative z-50">
                <div>
                    <label for="username" class="block text-sm font-medium text-gray-700">Email</label>
                    <input type="email" value="{{ last_username }}" name="_username" id="username" class="mt-1 block w-full px-3 py-2 border border-gray-300 rounded-md shadow-sm focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm" autocomplete="email" required autofocus>
                </div>

                <div>
                    <label for="password" class="block text-sm font-medium text-gray-700">Password</label>
                    <input type="password" name="_password" id="password" class="mt-1 block w-full px-3 py-2 border border-gray-300 rounded-md shadow-sm focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm" autocomplete="current-password" required>
                </div>

                <input type="hidden" name="_csrf_token" value="{{ csrf_token('authenticate') }}">

                <div>
                    <button type="submit" class="w-full flex justify-center py-2 px-4 border border-transparent rounded-md shadow-sm text-sm font-medium text-white bg-indigo-600 hover:bg-indigo-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500">
                        Sign in
                    </button>
                </div>
            </form>
        </div>
    </div>
{% endblock %}

日志错误信息

[2024-08-29T10:39:55.664038+00:00] security.INFO: Authenticator failed. {"exception":"[object] (Symfony\\Component\\Security\\Core\\Exception\\UserNotFoundException(code: 0): Username \"non@mail.com\" does not exist. at /Users/zitoune/Documents/orgaProjets/vendor/symfony/security-core/User/InMemoryUserProvider.php:101)","authenticator":"Symfony\\Component\\Security\\Http\\Authenticator\\FormLoginAuthenticator"} []

问题原因

日志显示系统使用InMemoryUserProvider查找用户,说明当前security.yaml配置默认启用了内存用户提供者,而非连接数据库的Doctrine用户提供者,因此无法找到PHPMyAdmin中存储的用户。

解决方案

1. 修正security.yaml配置

编辑config/packages/security.yaml,配置Doctrine用户提供者,确保防火墙使用该提供者:

security:
    enable_authenticator_manager: true
    password_hashers:
        # 指向你的User实体
        App\Entity\User: 'auto'
    providers:
        app_user_provider:
            entity:
                class: App\Entity\User
                property: email # 与登录表单提交的用户名字段对应(此处为邮箱)
    firewalls:
        dev:
            pattern: ^/(_(profiler|wdt)|css|images|js)/
            security: false
        main:
            lazy: true
            provider: app_user_provider # 指定使用上面定义的Doctrine用户提供者
            form_login:
                login_path: app_login
                check_path: app_login
                enable_csrf: true
            logout:
                path: app_logout

2. 确保User实体实现UserInterface

你的App\Entity\User必须正确实现Symfony的UserInterface,示例核心代码:

<?php
namespace App\Entity;

use Doctrine\ORM\Mapping as ORM;
use Symfony\Component\Security\Core\User\UserInterface;

#[ORM\Entity(repositoryClass: UserRepository::class)]
class User implements UserInterface
{
    #[ORM\Id]
    #[ORM\GeneratedValue]
    #[ORM\Column(type: 'integer')]
    private $id;

    #[ORM\Column(type: 'string', length: 180, unique: true)]
    private $email;

    #[ORM\Column(type: 'json')]
    private $roles = [];

    #[ORM\Column(type: 'string')]
    private $password;

    // 实现UserInterface的核心方法
    public function getUserIdentifier(): string
    {
        return (string) $this->email;
    }

    public function getRoles(): array
    {
        $roles = $this->roles;
        $roles[] = 'ROLE_USER';
        return array_unique($roles);
    }

    public function getPassword(): string
    {
        return $this->password;
    }

    public function eraseCredentials(): void
    {
        // 可选:清除敏感数据
    }

    // 实现剩余的UserInterface方法(默认返回true即可)
    public function isAccountNonExpired(): bool
    {
        return true;
    }

    public function isAccountNonLocked(): bool
    {
        return true;
    }

    public function isCredentialsNonExpired(): bool
    {
        return true;
    }

    public function isEnabled(): bool
    {
        return true;
    }

    // 其他getter/setter方法
    public function getEmail(): string
    {
        return $this->email;
    }

    public function setEmail(string $email): self
    {
        $this->email = $email;
        return $this;
    }

    public function setPassword(string $password): self
    {
        $this->password = $password;
        return $this;
    }
}

3. 确保密码已正确哈希存储

创建用户时,必须使用Symfony的UserPasswordHasherInterface对明文密码进行哈希,示例代码:

// 示例:在控制器或命令中创建用户
use App\Entity\User;
use Doctrine\ORM\EntityManagerInterface;
use Symfony\Component\PasswordHasher\Hasher\UserPasswordHasherInterface;

// ...
public function createUser(UserPasswordHasherInterface $passwordHasher, EntityManagerInterface $em)
{
    $user = new User();
    $user->setEmail('non@mail.com');
    $hashedPassword = $passwordHasher->hashPassword($user, 'your_plain_password');
    $user->setPassword($hashedPassword);
    $user->setRoles(['ROLE_USER']);

    $em->persist($user);
    $em->flush();
}

4. 验证配置正确性

运行以下命令检查配置是否有效:

php bin/console debug:config security

若有配置错误,命令会提示具体问题,根据提示修正即可。


内容的提问来源于stack exchange,提问作者Iam Eclipse

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.19 06:00:56