Linq执行不区分大小写的比较

时间:2011-10-20 11:09:06

标签: c# linq entity-framework

我只想在确切密码和大小写匹配时才需要用户对象。但是,即使密码的大小写不同,此查询也会获取结果:

db.Users.Where(u => u.Username.ToLower() == username.ToLower() &&
                        u.Password == password).FirstOrDefault();

我错过了什么?

7 个答案:

答案 0 :(得分:7)

最简单的方法是根据区分大小写的规则在DB中进行用户名匹配,并在其区分大小写的规则下使用.NET中的密码匹配:

db.Users.Where(u => u.Username == username).ToList().Where(u => u.Password == password).FirstOrDefault();

ToList()从基于数据库的LINQ转移到基于对象的LINQ,并且由于无论如何只有一个匹配的情况,这样做的性能影响可以忽略不计。

仍有将密码存储在数据库中的问题!

答案 1 :(得分:3)

如果数据库配置为不区分大小写,那么无法让它对密码进行区分大小写的比较(除非您诉诸TSQL tricks)。然而!您 不应该存储 密码 - 您应该存储盐渍哈希(理想情况下每个用户加盐)。并且散列(作为blob)应该可以用这种方式进行比较。

答案 2 :(得分:2)

尝试:

db.Users.Where(u => string.Compare(u.Username, username, System.StringComparison.OrdinalIngoreCase) == 0 &&
                    string.Compare(u.Password, password) == 0).FirstOrDefault();

因为这是在SQL中执行的,所以不能使用.NET / Linq比较方法。

答案 3 :(得分:1)

更改Password表中Users列的排序规则,以使用区分大小写的排序规则,例如Latin1_General_CS_AS。

或者,正如其他人所评论的那样,请考虑将解决方案更改为存储密码的哈希值(例如SHA1哈希值)并比较散列值而不是明文密码。

答案 4 :(得分:1)

您使用的是什么是密码的数据库类型以及整理序列?

它是VARCHAR并且您使用不区分大小写的排序规则,您描述的行为正是预期的行为。

某些数据库的默认排序规则序列可能不区分大小写(例如,请查看SQL SERVER – Collate – Case Sensitive SQL Query Search),因此您可能在不知情的情况下使用不区分大小写的排序规则。显然,您需要更改排序规则以获得正确的结果。

答案 5 :(得分:0)

如果u.Passwordpassword属于字符串类型,那么您的代码应该按预期工作。

答案 6 :(得分:0)

尝试改变您的列:

alter table [Users] alter column [password] nvarchar(100) collate Chinese_PRC_CS_AI