Как хэшировать пароль с SHA-512 в Java?
Я немного изучал методы шифрования строк Java, и, к сожалению, я не нашел хорошего учебника, как хэшировать строку с SHA-512 на Java; я прочитал несколько блогов о MD5 и Base64, но они не так безопасны, как я хотел бы (на самом деле, Base64 не является методом шифрования), поэтому я предпочитаю SHA-512.
8 ответов
вы можете использовать это для SHA-512
import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
public String get_SHA_512_SecurePassword(String passwordToHash, String salt){
String generatedPassword = null;
try {
MessageDigest md = MessageDigest.getInstance("SHA-512");
md.update(salt.getBytes(StandardCharsets.UTF_8));
byte[] bytes = md.digest(passwordToHash.getBytes(StandardCharsets.UTF_8));
StringBuilder sb = new StringBuilder();
for(int i=0; i< bytes.length ;i++){
sb.append(Integer.toString((bytes[i] & 0xff) + 0x100, 16).substring(1));
}
generatedPassword = sb.toString();
}
catch (NoSuchAlgorithmException e){
e.printStackTrace();
}
return generatedPassword;
}
пожалуйста, прекратите использовать хэш-функции для кодирования паролей! Они не обеспечивают необходимой защиты. Вместо этого вы должны использовать алгоритм PBKDF2, bcrypt или алгоритме Scrypt.
ссылки:
- http://blog.tjll.net/please-stop-hashing-passwords/
- http://security.blogoverflow.com/2011/11/why-passwords-should-be-hashed/
- https://crackstation.net/hashing-security.htm
- http://www.sitepoint.com/risks-challenges-password-hashing/
- http://security.blogoverflow.com/2013/09/about-secure-password-hashing/
используйте Apache Commons Crypt, он имеет функции crypt () на основе SHA-512, которые генерируют соленые хэши, которые даже совместимы с криптой libc и, следовательно, могут использоваться в PHP/Perl/Python/C и большинстве баз данных.
вы можете использовать это для хэша пароля в java, если хотите.
public static boolean isHashMatch(String password, // the password you want to check.
String saltedHash, // the salted hash you want to check your password against.
String hashAlgorithm, // the algorithm you want to use.
String delimiter) throws NoSuchAlgorithmException // the delimiter that has been used to delimit the salt and the hash.
{
// get the salt from the salted hash and decode it into a byte[].
byte[] salt = Base64.getDecoder()
.decode(saltedHash.split(delimiter)[0]);
// compute a new salted hash based on the provided password and salt.
String pw_saltedHash = computeSaltedBase64Hash(password,
salt,
hashAlgorithm,
delimiter);
// check if the provided salted hash matches the salted hash we computed from the password and salt.
return saltedHash.equals(pw_saltedHash);
}
public static String computeSaltedBase64Hash(String password, // the password you want to hash
String hashAlgorithm, // the algorithm you want to use.
String delimiter) throws NoSuchAlgorithmException // the delimiter that will be used to delimit the salt and the hash.
{
// compute the salted hash with a random salt.
return computeSaltedBase64Hash(password, null, hashAlgorithm, delimiter);
}
public static String computeSaltedBase64Hash(String password, // the password you want to hash
byte[] salt, // the salt you want to use (uses random salt if null).
String hashAlgorithm, // the algorithm you want to use.
String delimiter) throws NoSuchAlgorithmException // the delimiter that will be used to delimit the salt and the hash.
{
// transform the password string into a byte[]. we have to do this to work with it later.
byte[] passwordBytes = password.getBytes();
byte[] saltBytes;
if(salt != null)
{
saltBytes = salt;
}
else
{
// if null has been provided as salt parameter create a new random salt.
saltBytes = new byte[64];
SecureRandom secureRandom = new SecureRandom();
secureRandom.nextBytes(saltBytes);
}
// MessageDigest converts our password and salt into a hash.
MessageDigest messageDigest = MessageDigest.getInstance(hashAlgorithm);
// concatenate the salt byte[] and the password byte[].
byte[] saltAndPassword = concatArrays(saltBytes, passwordBytes);
// create the hash from our concatenated byte[].
byte[] saltedHash = messageDigest.digest(saltAndPassword);
// get java's base64 encoder for encoding.
Encoder base64Encoder = Base64.getEncoder();
// create a StringBuilder to build the result.
StringBuilder result = new StringBuilder();
result.append(base64Encoder.encodeToString(saltBytes)) // base64-encode the salt and append it.
.append(delimiter) // append the delimiter (watch out! don't use regex expressions as delimiter if you plan to use String.split() to isolate the salt!)
.append(base64Encoder.encodeToString(saltedHash)); // base64-encode the salted hash and append it.
// return a salt and salted hash combo.
return result.toString();
}
public static byte[] concatArrays(byte[]... arrays)
{
int concatLength = 0;
// get the actual length of all arrays and add it so we know how long our concatenated array has to be.
for(int i = 0; i< arrays.length; i++)
{
concatLength = concatLength + arrays[i].length;
}
// prepare our concatenated array which we're going to return later.
byte[] concatArray = new byte[concatLength];
// this index tells us where we write into our array.
int index = 0;
// concatenate the arrays.
for(int i = 0; i < arrays.length; i++)
{
for(int j = 0; j < arrays[i].length; j++)
{
concatArray[index] = arrays[i][j];
index++;
}
}
// return the concatenated arrays.
return concatArray;
}
import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import org.apache.commons.codec.binary.Hex;
public String getHashSHA512(String StringToHash, String salt){
String generatedPassword = null;
try {
MessageDigest md = MessageDigest.getInstance("SHA-512");
md.update(salt.getBytes(StandardCharsets.UTF_8));
byte[] bytes = md.digest(StringToHash.getBytes(StandardCharsets.UTF_8));
generatedPassword = Hex.encodeHexString(bytes);
}
catch (NoSuchAlgorithmException e){
e.printStackTrace();
}
return generatedPassword;
}
Не рекомендуется использовать хэш-функций паролей, хотя, новые alogrithms как bcrypt или scrypt в существование
С помощью гуавы:
Hashing.sha512().hashString(s, StandardCharsets.UTF_8).toString()
следующие стандартные алгоритмы хеширования предоставлено Java MessageDigest:
- MD2
- MD5 в
- ша-1
- SHA-256
- SHA-384
- SHA-512
вы можете проверить имя, которое вы предоставляете заводскому методу.
С безопасным хэшированием объедините 3 компонента соли (по 150 случайных символов каждый) в отдельную соль пользователя (соль пользователя из таблицы базы данных пользователя, общая соль в таблице базы данных (ежемесячное изменение с заданием cron) и спрячьте соль в библиотеке приложений). Выровняйте количество цикла for безопасного хэша с вашими потребностями. См. ответ выше для метода хэширования.
private static String generateSalt(int lenght){
String abcCapitals = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
String abcLowerCase = "abcdefghijklmnopqrstuvwxyz";
String numbers = "01234567890123456789";
String characters = "!@#$%^&*!@#$%%^^&*";
String total = abcCapitals + abcLowerCase + numbers + characters;
String response = "";
char letters[] = new char[lenght];
for (int i=0; i<lenght-1; i++){
Random r = new Random();
char letter = total.charAt(r.nextInt(total.length()));
letters[i] = letter;
}
response = Arrays.toString(letters).replaceAll("\s+","");
response = response.replaceAll(",","");
return response;
}
private static String getHash(String passwordToHash, String salt){
String generatedPassword = null;
try {
MessageDigest md = MessageDigest.getInstance("SHA-512");
md.update(salt.getBytes(StandardCharsets.UTF_8));
byte[] bytes = md.digest(passwordToHash.getBytes(StandardCharsets.UTF_8));
StringBuilder sb = new StringBuilder();
for(int i=0; i< bytes.length ;i++){
sb.append(Integer.toString((bytes[i] & 0xff) + 0x100, 16).substring(1));
}
generatedPassword = sb.toString();
}
catch (NoSuchAlgorithmException e){
System.out.println(e);
}
return generatedPassword;
}
public static String getSecureHash(String password, String salt){
String hash = getHash(password, salt);
for (int i=0; i<20000; i++){
hash = getHash(password, hash);
}
return hash;
}
/**
* @param args the command line arguments
*/
public static void main(String[] args) {
String salt = generateSalt(150);
String salt2 = generateSalt(150);
String salt3 = generateSalt(150);
String someString = "This is some string!";
String hash = getSecureHash(someString, salt + salt2 + salt3);
System.out.println(hash);
}