密码散列以前是有效的,现在我无法进入我的软件

本文关键字:软件 我的 有效 密码 | 更新日期: 2023-09-27 18:02:49

我根据这篇代码项目文章对我的登录进行了加盐和散列处理

当我这样做时,数据库中的密码和盐字段只是varchar列。数据在SQL Server Management Studio中显示为问号。

然后一个朋友来了,把列改成了nvarchar数据类型,现在数据似乎是亚洲字母/单词的集合——我想这对那些读任何语言的人来说都没有意义。

现在的问题是,即使我创建了一个新用户,每次登录尝试都失败。

用户添加和登录

    public User Login() // returns an instance of its own class
    {
        // get the salt value for the user
        var auser = ie.users.FirstOrDefault(u => String.Compare(u.emailaddress, emailaddress, false) == 0);
        if (auser == null)
        {
            throw new ValidationException("User not found");
        }
        // hash the login for comparison to stored password hash
        HashGenerator h = new HashGenerator(password, auser.usersalt);
        string hash = h.GetHash();
        var us = ie.users.FirstOrDefault(u => String.Compare(u.emailaddress, emailaddress, false) == 0 && String.Compare(u.password, password, false) == 0);
        if (us == null)
        {
            throw new Exception("Invalid email address and/or password."); // seems here's where it goes wrong
        }
        User user = new User();
        user.userid = us.userid;
        user.storeid = us.storeid;
        user.role = us.role;
        return user; // login succeeded, return the data to the calling method
    }
    public void Add()
    {
        user newuser = new user();
        newuser.storeid = storeid;
        newuser.emailaddress = emailaddress;
        // Generate password hash
        string usersalt = SaltGenerator.GetSaltString();
        HashGenerator hash = new HashGenerator(password, usersalt);
        newuser.password = hash.GetHash();
        newuser.role = role;
        newuser.usersalt = usersalt;
        ie.users.Add(newuser);
        ie.SaveChanges();
    }

哈希和盐生成器

public class HashGenerator
{
    public string pass { get; protected set; }
    public string salt { get; protected set; }
    public HashGenerator(string Password, string Salt)
    {
        pass = Password;
        salt = Salt;
    }
    public string GetHash()
    {
        SHA512 sha = new SHA512CryptoServiceProvider();
        byte[] data = CryptUtility.GetBytes(String.Format("{0}{1}", pass, salt));
        byte[] hash = sha.ComputeHash(data);
        return CryptUtility.GetString(hash);
    }
}
public static class SaltGenerator
{
    private static RNGCryptoServiceProvider provider = null;
    private const int saltSize = 128;
    static SaltGenerator()
    {
        provider = new RNGCryptoServiceProvider();
    }
    public static string GetSaltString()
    {
        byte[] saltBytes = new byte[saltSize];
        provider.GetNonZeroBytes(saltBytes);
        return CryptUtility.GetString(saltBytes);
    }
}

获取字符串和字节的Crypt实用程序

class CryptUtility
{
    public static byte[] GetBytes(string Str)
    {
        byte[] bytes = new byte[Str.Length * sizeof(char)];
        System.Buffer.BlockCopy(Str.ToCharArray(), 0, bytes, 0, bytes.Length);
        return bytes;
    }
    public static string GetString(byte[] Bytes)
    {
        char[] chars = new char[Bytes.Length / sizeof(char)];
        System.Buffer.BlockCopy(Bytes, 0, chars, 0, Bytes.Length);
        return new string(chars);
    }
}

登录使用的工作,这段代码没有改变,从那时起…唯一改变的是users表中的password和salt列现在是nvarchar而不是varchar

也就是说,我想我应该用上面的add方法创建一个新用户,但是用这个用户登录也失败了。

我真的不知道如何解决这个问题。如果我不能访问它进行测试,我就不能继续开发系统的其余部分。

任何帮助将非常感激!

密码散列以前是有效的,现在我无法进入我的软件

嗯,你不应该使用

这个变量吗?

哈希

为比较?

    // hash the login for comparison to stored password hash
    HashGenerator h = new HashGenerator(password, auser.usersalt);
    string hash = h.GetHash();
    var us = ie.users.FirstOrDefault(u => String.Compare(u.emailaddress, emailaddress, false) == 0 && String.Compare(u.password, hash, false) == 0);

进行db备份并转换回varchar。或回滚到转换前的备份。似乎你的朋友在将数据类型转换为nvarchar时做错了什么。