我正在配置对.NET Core上使用C#构建的RESTful Web API的身份验证。我的团队正在使用Entity Framework与我们的PostgreSQL数据库进行交互。 我们保存在数据库中的用户密码使用SHA256进行哈希处理。 当客户/用户尝试通过我们的API进行身份验证时,我们使用共享密钥解密其密码,然后使用SHA256对其进行哈希处理,并将结果与数据库中的哈希密码进行比较。 现在,我正在用一个示例用户测试代码,它的哈希密码如下所示(并保存在数据库中):?-e> $?n \ u 000f ?? tw: $ ???? \ u 0017et ?? |?J?k ??? S。注意两个“ \ u”。不幸的是,似乎Entity Framework会将它们解释为转义符,并且在检索User对象(带有其Password属性)时,会自动添加另一个 \ ,将 \ u 转换为 \\ u 。
在下图中,上半部分显示了哈希密码保存在数据库中时的密码,下半部分显示了Entity以我所解释的方式对其进行修改的方式。
从请求中收到的密码(由代码散列)与数据库上的密码匹配,如下所示: Hashed Password
试图操纵字符串是没有讨论的:它是一个哈希密码,因此没有实际的模式可循,而且我无法真正预期Entity将如何解释和修改 \ 和类似转义的字符字符或子字符串。
我的解决方法使用了 Regex.Unescape(),但是由于Microsoft itself所说的精度不能100%,所以我不喜欢它。
在这段代码中, password 是我从请求中获得的字符串。我使用SHA256对其进行哈希处理,并将其分配给 hashedPassword 。查询数据库时,我需要一个用户名( Client ),其用户名和密码与我从请求中获得的 username 和 hashedPassword 相同。如果没有 Regex.Unescape(),则由Entity Framework检索的字符串与 hashedPassword 不匹配(尽管正如我所解释的,它实际上在数据库上也是如此)。
else
{
using (SHA256Managed shaHasher = new SHA256Managed())
{
byte[] hashResult = shaHasher.ComputeHash(Encoding.ASCII.GetBytes(password));
hashedPassword = Encoding.ASCII.GetString(hashResult);
}
}
using (MasterDataContext context = new MasterDataContext())
{
try
{
user = await Task.Run<Client>(() =>
context.Client
.SingleOrDefault<Client>(
c => c.UserName.Equals(username)
&& Regex.Unescape(c.Password).Equals(hashedPassword)));
}
}
这很糟糕,我只是想直接从数据库中直接获取我的字符串,而没有实体故意修改它,但是我不知道该怎么做。