请原谅我的无知,那到底是什么意思?
我使用Java编写该应用程序。因此,我的计划是使用Apache Commons Digest Utils SHA512对userID、人名和一些Math.random()值进行哈希,并将该哈希字符串与userID和人名一起传递。
这是标准做法吗? 我应该将盐也传递给第三方,对吗?
通常用盐来安全地存储密码的哈希值。对密码进行哈希以便于存储或通信(以使其不能被他人读取)会容易受到使用彩虹表进行解码的攻击。现在,当您将一个随机字符串添加到密码中,但将该字符串与哈希一起存储时,这变得更加困难。计算这个新哈希的方法如下:
hash(password + salt)
甚至可以
hash(hash(password) + salt)
为了安全地登录第三方网站,可以发送用户ID、加盐的哈希值(来自上面)以及所使用的盐(如果未提供)。根据该网站存储密码的方式,您可以自行生成盐,也可以向其请求盐。
一种选项是首先将用户ID发送到网站,然后让其响应盐,然后将hash(password+salt))
发送回网站。
在Java中,您可以这样做:
import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.lang.RandomStringUtils;
/**
* SHA1-hash the password with the user's salt.
*
* @param password
*/
public void setPassword(String password)
{
if (password.equals(this.password))
{
return;
}
if (passwordSalt == null || passwordSalt.equals(""))
{
passwordSalt = RandomStringUtils.randomAscii(20);
}
this.password = DigestUtils.shaHex(password + passwordSalt);
}
/**
* Check if a given password is correct.
*
* @param givenPassword
* @return True is correct, else false.
*/
public boolean checkPassword(String givenPassword)
{
return (password.equals(DigestUtils.shaHex(givenPassword + passwordSalt)));
}
我建议你在使用这个第三方应用程序时,尽可能找到更多信息或一些示例。根据你所描述的情况,这似乎不是常见的做法,而且基于你所说的也没有太多意义。
你在程序中对用户进行身份验证(有几个答案似乎正在解决这个问题,是的,你应该将用户密码存储为加盐哈希值,但这是另一个问题),然后,在验证他们之后,将一些信息传递给这个第三方应用程序。现在,这取决于这个应用程序需要做什么/知道什么。例如,如果它需要知道userID,那么在提交之前就不能对其进行哈希/加盐,因为该应用程序将永远无法获取原始的userID。另一方面,如果该应用程序只需要某种标识符来识别请求,并且将userID + userName哈希化只是一个建议,则这是有意义的,你基本上为第三方应用程序生成了一个用户唯一但不可解码的字符串,作为会话密钥。
如果他们试图让你采取第二种路线,这是一种有点奇怪(并且不太安全)的处理请求的方式,但在我看来还可以接受。
就像我说的那样,看看能否找到一些例子,或者如果你想在这里发布有关该应用程序的更多信息,我们可以自己看一下。
盐的整个意义在于使使用所谓的“彩虹表”进行攻击变得不可行(从概率角度来看:如果你采用足够大的哈希值,则事实上将不可能预计算彩虹表)。
http://en.wikipedia.org/wiki/Rainbow_table
不要只是对一个哈希值(a)进行哈希处理并存储该哈希值:
:460526e74fd6a25b525e642db2f756a4:
你需要执行hash(a + salt)操作,并且存储哈希值和盐值(盐值可以随机选择):
:cdd5bc3f05f6a76f6c82af728b2c555c:346884e6e35be: