All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.siashan.toolkit.crypt.digest.Crypt Maven / Gradle / Ivy

package com.siashan.toolkit.crypt.digest;

import java.nio.charset.StandardCharsets;
import java.security.SecureRandom;

/**
 * GNU libc crypt(3)兼容哈希方法.
 *
 * 这个类是不可变的,并且是线程安全的.
 * @author siashan
 * @since 1.0.7
 */
public class Crypt {

    /**
     * 以与密码(3)兼容的方式加密密码.
     * 

* 使用随机salt和默认算法(当前为SHA-512). *

*

* * @param keyBytes * 明文密码 * @return 哈希值 */ public static String crypt(final byte[] keyBytes) { return crypt(keyBytes, null); } /** * 以与密码(3)兼容的方式加密密码. *

* 如果未提供salt,则将使用随机salt和默认算法(当前为SHA-512). * * @param keyBytes * 明文密码 * @param salt * 不带前缀或“rounds=”的实际盐值。 * 盐可能是空的,在这种情况下,将使用{@link-ThreadLocalRandom}为您生成一个salt; * 对于更安全的盐,请考虑使用{Link SaleRealDANDOM }生成你自己的盐。 * @return 哈希值 */ public static String crypt(final byte[] keyBytes, final String salt) { if (salt == null) { return Sha2Crypt.sha512Crypt(keyBytes); } else if (salt.startsWith(Sha2Crypt.SHA512_PREFIX)) { return Sha2Crypt.sha512Crypt(keyBytes, salt); } else if (salt.startsWith(Sha2Crypt.SHA256_PREFIX)) { return Sha2Crypt.sha256Crypt(keyBytes, salt); } else if (salt.startsWith(Md5Crypt.MD5_PREFIX)) { return Md5Crypt.md5Crypt(keyBytes, salt); } else { return UnixCrypt.crypt(keyBytes, salt); } } /** * 使用最强加密(3)算法计算摘要. *

* 使用随机salt和默认算法(当前为SHA-512)。 *

*

* 使用{@link-ThreadLocalRandom}为您生成一个salt; * 为了更安全的盐考虑使用{@link SecureRandom}生成您自己的salt并调用{@link#crypt(String,String)}. *

* * @param key * 明文密码 * @return 哈希值 */ public static String crypt(final String key) { return crypt(key, null); } /** * 以与密码(3)兼容的方式加密密码. *

* 精确的算法取决于salt字符串的格式: *

    *
  • SHA-512盐以{@code$6$}开头,最长可达16个字符. *
  • SHA-256盐以{@code$5$}开头,最长可达16个字符 *
  • MD5盐以{@code$1$}开头,最长可达8个字符 *
  • DES,传统的UnixCrypt算法仅使用2个字符 *
  • DES算法中只使用密码的前8个字符! *
* 此方法无法识别神奇字符串{@code“$apr1$”}和{@code“$2a$”},因为其输出应该是与libc实现相同。 *

* 盐串的其余部分从集合{@code[a-zA-Z0-9./]}中提取, * 并在a的最大长度处切割遇到{@code“$”}符号。 * 因此,输入完整的哈希值作为salt是有效的,例如验证密码为: * *

     * storedPwd.equals(crypt(enteredPwd, storedPwd))
     * 
*

* 结果字符串以标记字符串({@code$n$})开头,其中n与输入字符串相同. * 然后附加salt,后跟{@code“$”}符号. * 后面是实际的散列值. * 对于DES,字符串只包含salt和实际哈希. * 总长度取决于使用的算法: *

    *
  • SHA-512:106个字符 *
  • SHA-256: 63 个字符 *
  • MD5: 34 个字符 *
  • DES: 13 个字符 *
*

* Example: * *

     *      crypt("secret", "$1$xxxx") => "$1$xxxx$aMkevjfEIpa35Bh3G4bAc."
     *      crypt("secret", "xx") => "xxWAum7tHdIUw"
     * 
*

* 此方法的变体接受byte[]数组以支持未编码的输入字符串UTF-8, * 但例如在ISO-8859-1中,相同的字符导致不同的字节值. * * @param key * 由所用用户输入的明文密码 * @param salt * 不带前缀或“rounds=”的实际盐值。 * 盐可能为空,在这种情况下salt是使用{@link-ThreadLocalRandom}为您生成的; * 为了更安全的盐考虑使用{@Link SoalEnrand On}来生成自己的盐。 * @return 散列值,即包括salt字符串的加密密码 */ public static String crypt(final String key, final String salt) { return crypt(key.getBytes(StandardCharsets.UTF_8), salt); } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy