package security;
import java.io.*;
import java.security. *;
import javax.crypto. *;
/**
* 密钥:算法产生的加密种子
* 密码:没有什么好解释的,登陆论坛还要呢
* 算法:可以上升为数学理论
* 举个例子,你的密码是123,但是明文发送容易被人盗取
* 你用某个算法加密,密钥是:53csif253a6jt342fd621
* 传输的便是加密过的数据,比如:fasetqrlkerqoiruq53qrqewlkjrlfasdfa41解密也需要密钥
* 加密密钥和解密密钥可以相同(对称加密算法),也可以不相同(非对称算法)
*/
public class Eryptogram
{
public String Algorithm ="DES";//定义 加密算法,可用 DES,DESede,Blowfish
public boolean debug = false ;//调试时使用
/**
* 生成密钥,随机生成,目前只作用于演示
* @return byte[] 返回生成的密钥
* @throws exception 扔出异常.
*/
public byte[] getSecretKey() throws Exception {
KeyGenerator keygen = KeyGenerator.getInstance(Algorithm);
SecretKey deskey = keygen.generateKey();
if (debug)
System.out.println("生成密钥:" + byte2hex(deskey.getEncoded()));
return deskey.getEncoded();
}
/**
* 将指定的数据根据提供的密钥进行加密
* @param input 需要加密的数据
* @param key 密钥
* @return byte[] 加密后的数据
* @throws Exception
*/
public byte[] encryptData(byte[] input, byte[] key) throws Exception {
SecretKey deskey = new javax.crypto.spec.SecretKeySpec(key, Algorithm);
if (debug) {
System.out.println("加密前的字符串:" + new String(input));
System.out.println("加密前的二进串:" + byte2hex(input));
}
Cipher c1 = Cipher.getInstance(Algorithm);
c1.init(Cipher.ENCRYPT_MODE, deskey);
byte[] cipherByte = c1.doFinal(input);
if (debug)
System.out.println("加密后的二进串:" + byte2hex(cipherByte));
return cipherByte;
}
/**
* 将给定的已加密的数据通过指定的密钥进行解密
* @param input 待解密的数据
* @param key 密钥
* @return byte[] 解密后的数据
* @throws Exception
*/
public byte[] decryptData(byte[] input, byte[] key) throws Exception {
SecretKey deskey = new javax.crypto.spec.SecretKeySpec(key, Algorithm);
if (debug)
System.out.println("解密前的信息:" + byte2hex(input));
Cipher c1 = Cipher.getInstance(Algorithm);
c1.init(Cipher.DECRYPT_MODE, deskey);
byte[] clearByte = c1.doFinal(input);
if (debug) {
System.out.println("解密后的二进串:" + byte2hex(clearByte));
System.out.println("解密后的字符串:" + (new String(clearByte)));
}
return clearByte;
}
/**
* Description: 对密码进行MD5加密(非对称加密,不能解密,适用于密码匹配)
* @param : String pwd
* @return: String
* @throws AppException
*/
public String encrypt(String pwd) throws NoSuchAlgorithmException{
MessageDigest md = MessageDigest.getInstance("MD5");
md.update(pwd.getBytes());
byte[] result = md.digest();
return byte2Str(result);
}
/**
* 字节码转换成16进制字符串
* @param byte[]b 输入要转换的字节码
* @return String 返回转换后的16进制字符串
*/
public String byte2hex(byte[] b) {
String hs = "";
String stmp = "";
for (int n = 0; n < b.length; n++) {
stmp = (java.lang.Integer.toHexString(b[n] & 0XFF));
if (stmp.length() == 1)
hs = hs + "0" + stmp;
else
hs = hs + stmp;
if (n < b.length - 1)
hs = hs + ":";
}
return hs.toUpperCase();
}
/**
* int类型转换为byte[]类型
* @param input 待转换的int值
* @return byte[]
*/
public byte[] intTobyte(int input) {
byte[] output = new byte[4];
output[0] = (byte) (input & 0xff);
output[1] = (byte) ((input >> 8) & 0xff);
output[2] = (byte) ((input >> 16) & 0xff);
output[3] = (byte) (input >>> 24);
return output;
}
/**
* byte[]类型转换为int类型
* @param input 待转换的byte值
* @return int
*/
public int byteToint(byte[] input) {
int output = 0;
if (input.length != 4) {
System.out.println("byte类型转换为int类型时发生错误!");
System.exit(-1);
}
output = (input[0] & 0xff) | ((input[1] << 8) & 0xff00)
| ((input[2] << 24) >>> 8) | (input[3] << 24);
return output;
}
/**
* Description: 二行制转字符串
* @param : byte[]
* @return: String
* @throws AppException
*/
private String byte2Str(byte[] b) {
String hs = "";
String stmp = "";
for (int n = 0; n < b.length; n++) {
stmp = (Integer.toHexString(b[n] & 0XFF));
if (stmp.length() == 1) {
hs = hs + "0" + stmp;
} else {
hs = hs + stmp;
}
if (n < (b.length - 1)) {
hs = hs + "";
}
}
return hs;
}
public static void main(String[] args) {
try {//过程演示,普通的加解密操作
Eryptogram etg = new Eryptogram();
etg.debug = true;
byte[] key = etg.getSecretKey();
String aa = "0123456789中文测试EnglishTest!%$#@!~~";
byte[] en = etg.encryptData(aa.getBytes(), key);
/*********************************************************/
/*为了将加密数据写入文件但不出现错误,目前的方法是转为int类型进行存储*/
/*********************************************************/
int[] intTemp = new int[en.length/4];
for (int i = 0; i < intTemp.length; i++) {
byte[] byteTemp = new byte[4];
byteTemp[0] = en[i*4+0];
byteTemp[1] = en[i*4+1];
byteTemp[2] = en[i*4+2];
byteTemp[3] = en[i*4+3];
intTemp[i] = etg.byteToint(byteTemp);
// System.out.println("intTemp["+i+"]="+intTemp[i]);
}
/*********************************************************/
/*待提取文件内容后,将int转化为byte即可进行解密 */
/*********************************************************/
byte[] decodeTemp = new byte[intTemp.length*4];
for (int i = 0; i < intTemp.length; i++) {
byte[] byteTemp = etg.intTobyte(intTemp[i]);
decodeTemp[i*4+0] = byteTemp[0];
decodeTemp[i*4+1] = byteTemp[1];
decodeTemp[i*4+2] = byteTemp[2];
decodeTemp[i*4+3] = byteTemp[3];
}
byte[] de = etg.decryptData(decodeTemp, key);
} catch (Exception e) {
// TODO: handle exception
e.printStackTrace();
}
try {//MD5非对称加密
Eryptogram etg = new Eryptogram();
System.out.println("对‘01234567’进行MD5加密后的结果:"+etg.encrypt("01234567"));
} catch (Exception e) {
// TODO: handle exception
e.printStackTrace();
}
}
}