import java.io.UnsupportedEncodingException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
import java.util.Arrays;
import java.util.Scanner;
public class MD5{
private static final String HEX_NUMS_STR="0123456789ABCDEF";
private static final Integer SALT_LENGTH = 12;
/**
* Converted into a byte array a hexadecimal character string
* @param hex
* @return
*/
public static byte[] hexStringToByte(String hex) {
int len = (hex.length() / 2);
byte[] result = new byte[len];
char[] hexChars = hex.toCharArray();
for (int i = 0; i < len; i++) {
int pos = i * 2;
result[i] = (byte)(HEX_NUMS_STR.indexOf(hexChars[pos]) << 4 | HEX_NUMS_STR.indexOf(hexChars[pos + 1]));
}
return result;
}
/**
* Convert the specified byte array into a hexadecimal character string
* @param b
* @return
*/
public static String byteToHexString(byte[] b) {
StringBuffer hexString = new StringBuffer();
for (int i = 0; i < b.length; i++) {
// 0XFF decimal 255, wherein the java 0X is stated to hexadecimal characters used, this time taking the current byte represents the inverted
String hex = Integer.toHexString(b[i] & 0xFF);
if (hex.length() == 1) {
hex = '0' + hex;
}
hexString.append(hex.toUpperCase());
}
return hexString.toString();
}
/**
* 16 hexadecimal form obtained after the encrypted string
* @param password
* @return
* @throws NoSuchAlgorithmException
* @throws UnsupportedEncodingException
*/
public static String getEncryptedPwd(String sourceString)
throws NoSuchAlgorithmException, UnsupportedEncodingException {
// Declare the array variable encrypted passwords
byte[] pwd = null;
// random number generator
SecureRandom random = new SecureRandom();
// declare array variables salt
byte[] salt = new byte[SALT_LENGTH];
// the random number into the variable salt
random.nextBytes(salt);
// declare the message digest object
MessageDigest md = null;
// create a message digest
md = MessageDigest.getInstance("MD5");
// the data incoming message digest object salt
md.update(salt);
// the password data to the target message digest
md.update(sourceString.getBytes("UTF-8"));
// get the message digest array of bytes
byte[] digest = md.digest();
// Because salt byte array to be stored in the password, the byte length plus salt
pwd = new byte[digest.length + SALT_LENGTH];
// salt bytes to copy the first 12 bytes of the byte array generated encrypted password to a password authentication when taken salt
System.arraycopy(salt, 0, pwd, 0, SALT_LENGTH);
// byte message digest encrypted passwords are copied to the start byte array from the 13th byte
System.arraycopy(digest, 0, pwd, SALT_LENGTH, digest.length);
// the password to encrypt the byte array form is converted to a hexadecimal string format password
return byteToHexString(pwd);
}
/**
* Verify password is legitimate
* @param password
* @param passwordInDb
* @return
* @throws NoSuchAlgorithmException
* @throws UnsupportedEncodingException
*/
public static boolean validPassword(String sourceString, String md5String)
throws NoSuchAlgorithmException, UnsupportedEncodingException {
// hexadecimal string format to convert the password into a byte array
byte[] pwdInDb = hexStringToByte(md5String);
// declare variables salt
byte[] salt = new byte[SALT_LENGTH];
// save the password from the byte array salt extracted from the database
System.arraycopy(pwdInDb, 0, salt, 0, SALT_LENGTH);
// create the message digest object
MessageDigest md = MessageDigest.getInstance("MD5");
// the data incoming message digest object salt
md.update(salt);
// the password data to the target message digest
md.update(sourceString.getBytes("UTF-8"));
// password generated message digest
byte[] digest = md.digest();
// declare a variable holding the database password message digest
byte[] digestInDb = new byte[pwdInDb.length - SALT_LENGTH];
// get the message digest of the password database
System.arraycopy(pwdInDb, SALT_LENGTH, digestInDb, 0, digestInDb.length);
// whether the comparison according to the same password generated message digest and the message digest in the database
if (Arrays.equals(digest, digestInDb)) {
// returns the correct password matches the password messages
return true;
} else {
// password does not return the correct password does not match the message
return false;
}
}
public static void main(String[] args){
System.out.println ( "----------------- MD5 encryption start --------------------");
try {
System.out.print ( "----------------- Please enter you want to encrypt the contents of execution press enter:");
Scanner scanner = new Scanner(System.in);
String sourceString = scanner.nextLine();
String md5String = getEncryptedPwd(sourceString);
System.out.println ( "---------- before encryption:" + sourceString);
System.out.println ( "---------- after encryption:" + md5String);
boolean falg = validPassword(sourceString,md5String);
System.out.println ( "---------- check result input string:" + falg);
} catch (NoSuchAlgorithmException e) {
// TODO Auto-generated catch block
e.printStackTrace ();
} catch (UnsupportedEncodingException e) {
// TODO Auto-generated catch block
e.printStackTrace ();
}
System.out.println ( "----------------- MD5 encrypted end --------------------");
}
}