0

我需要基于 FirstName/LastName 组合构建一个哈希。在数据库中,每个最大值都是 100 个字符,并且哈希值最多需要 20 个字符。

有没有办法在此基础上可靠地产生独特的价值?假设 FirstName/LastName 组合是唯一的。

4

3 回答 3

2

哈希永远不能绝对保证是唯一的,它们不应该用作唯一标识符。

于 2012-11-12T03:25:31.433 回答
2

实际上,良好的加密哈希值几乎与它们各自的消息一样独特。您所描述的内容看起来非常像 SHA-1,如果您希望相同的 FirstName/LastName 映射到相同的“唯一”20 个字符。完整的 SHA-1 比 GUID 大(说明了什么),并且作为加密,分布相当均匀,不太可能发生冲突(参见 SHA-1 的冲突攻击——即使是故意的也很难做到)。

于 2012-11-12T03:35:29.537 回答
1

听起来您希望表中的每条记录都有一个唯一标识符,而且这个标识符不容易猜到。有多种方法可以实现这一目标,包括:

1.为带有unique约束的标识符添加一列,并在插入列时生成随机标识符。如果由于标识符已经存在而导致插入失败,请生成新标识符并重试。

2.在表中添加一auto GUID列,让数据库生成唯一标识符。

3.向表中添加一auto-increment int列,让数据库生成唯一标识符并对其进行混淆处理。例如,您可以通过将整数填充为 16 并使用 128 位分组密码对其进行加密来做到这一点。例子:

private static readonly AesManaged cipher = new AesManaged()
{
    BlockSize = 128,
    Key = Encoding.UTF8.GetBytes("secret__secret__"),
    Mode = CipherMode.ECB,
    Padding = PaddingMode.None
};

static string Obfuscate(int id)
{
    using (var transform = cipher.CreateEncryptor())
    {
        return Convert.ToBase64String(
            transform.TransformFinalBlock(
                Encoding.UTF8.GetBytes(
                    id.ToString("0000000000000000")), 0, 16));
    }
}

static int Deobfuscate(string s)
{
    using (var transform = cipher.CreateDecryptor())
    {
        return int.Parse(
            Encoding.UTF8.GetString(
                transform.TransformFinalBlock(
                    Convert.FromBase64String(s), 0, 16)));
    }
}

请注意,这些方法都无法猜测标识符,只是比将整数加 1 更困难。您仍然需要检查用户是否有权查看与标识符关联的信息。

于 2012-11-12T03:43:24.313 回答