Symfony2 中不区分大小写的用户名

Case-insensitive user-names in Symfony2

默认情况下,Symfony2 区分大小写匹配用户名。我希望用户能够输入 johnsmithJohnSmithjohnSMITH 或其任何变体,并让他们都注册为 johnsmith。我该怎么做?

我认为最简单的方法是在比较之前始终将每个用户名转换为小写。一方面这很容易做到(只需将 lower() 放入 SQL 语句中),但是对于用户在登录表单中输入的内容,我该如何做到这一点呢?由于 Symfony 自动处理 login_check 路由处理,我无法弄清楚。

更好的是,我可以设置一些选项来启用不区分大小写吗?

您是否尝试使用 CSS 将输入转换为小写?实际上有一些方法可以在将数据输入传递给 login_check 控制器之前对其进行控制,但是如果您想要快速修复:

p {
    text-transform: lowercase;
}

在您的 setUsername 中,您可以将文本更改为小写,例如..

public function setUsername($username)
{
    $this->username = mb_strtolower($username);

    return $this;
}

作为参考,FOSUserBundle 在 updateUser 调用中通过 "canonicalizing" 用户名(至 usernameCanonical)和电子邮件地址(至 canonicalEmail)处理此问题(参见 Doctrine\UserManager that calls the Canonicalizer) 然后用于搜索。

我觉得自己像个白痴。我所要做的就是在 SQL 语句中的 where 子句周围添加另一个 lower()。像这样:

select lower(USERNAME) as USERNAME, PASSWORD, ROLES, ALL_CUSTOMER_ACCESS
from COMPANYNAME_USERS
where lower(USERNAME) = lower(:username)

你已经修复了,但我会为有类似问题的用户解释另一种解决方案:

  1. 您必须以这种方式实现您自己的提供程序:http://symfony.com/doc/current/cookbook/security/entity_provider.html#authenticating-someone-with-a-custom-entity-provider
  2. 在方法 loadUserByUsername 中改用以下查询:

    $user = $this->findOneBy(array('username' => strtolower($username)));

这对我有用。 (也在 Doctrine Mongo ODM 中)

只需在UserRepository 中编写正确的loadUserByUsername 函数即可。 不能区分大小写:

public function loadUserByUsername($username)
{
    $user = $this->createQueryBuilder('u')
        ->where('LOWER(u.email) = :username')
        ->setParameter('username', strtolower($username))
        ->getQuery()
        ->getOneOrNullResult();

    if ($user){
       return $user;
    }

    throw new UsernameNotFoundException('Unable to find user "' . $username . '"');
}