package com.abc.core.utils;
import java.io.UnsupportedEncodingException;
import java.security.InvalidKeyException;
import java.security.Key;
import java.security.NoSuchAlgorithmException;
import javax.crypto.BadPaddingException;
import javax.crypto.Cipher;
import javax.crypto.IllegalBlockSizeException;
import javax.crypto.NoSuchPaddingException;
import javax.crypto.ShortBufferException;
import javax.crypto.spec.SecretKeySpec;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
/**
* 将数据使用DES算法加密,再进行base64编码,方便进行网络传输,支持中文。
* @author Administrator
*/
public class CipherBase64 {
@SuppressWarnings("unused")
private static Logger logger =LogManager.getLogger(CipherBase64.class);
private Key key;
private Cipher cipher;
private static CipherBase64 singltonEncrypt = null;
private static CipherBase64 singltonDecrypt = null;
@SuppressWarnings("unused")
private char[] alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/="
.toCharArray();
private byte[] codes = new byte[256];
/**
*
* 初始化,由于消耗内存过多,所以设置为private,只能用getInstance()方法生成一个对象
*
*/
private CipherBase64(String model) {
for (int i = 0; i < 256; i++)
codes[i] = -1;
for (int i = 'A'; i <= 'Z'; i++)
codes[i] = (byte) (i - 'A');
for (int i = 'a'; i <= 'z'; i++)
codes[i] = (byte) (26 + i - 'a');
for (int i = '0'; i <= '9'; i++)
codes[i] = (byte) (52 + i - '0');
codes['+'] = 62;
codes['/'] = 63;
try {
cipher = Cipher.getInstance(model);
} catch (NoSuchAlgorithmException e) {
singltonEncrypt = null;
singltonDecrypt = null;
logger.error(e.getMessage(), e);
} catch (NoSuchPaddingException e) {
singltonEncrypt = null;
singltonDecrypt = null;
logger.error(e.getMessage(), e);
}
}
public static CipherBase64 getSingltonDecryptInstance() throws InvalidKeyException {
if (singltonDecrypt == null) {
synchronized (CipherBase64.class) {
if (singltonDecrypt == null) {
CipherBase64 cipherBase = new CipherBase64("DES/ECB/NoPadding");
cipherBase.setKey(SystemParaUtil.SECRET_KEY);
cipherBase.initDecrypt();
singltonDecrypt = cipherBase;
}
}
}
return singltonDecrypt;
}
public static CipherBase64 getSingltonEncryptInstance() throws InvalidKeyException {
if (singltonEncrypt == null) {
synchronized (CipherBase64.class) {
if (singltonEncrypt == null) {
CipherBase64 cipherBase = new CipherBase64("DES");
cipherBase.setKey(SystemParaUtil.SECRET_KEY);
cipherBase.initEncrypt();
singltonEncrypt = cipherBase;
}
}
}
return singltonEncrypt;
}
/**
*
*
* 加密
* @param sourceString
* @return
* @throws InvalidKeyException
* @throws UnsupportedEncodingException
* @throws IllegalStateException
* @throws IllegalBlockSizeException
* @throws BadPaddingException
*/
private String encrpt(String sourceString) throws InvalidKeyException,
UnsupportedEncodingException, IllegalStateException,
IllegalBlockSizeException, BadPaddingException {
String cryptedString = null;
int cypheredBytes = 0;
byte[] inputBytes = sourceString.getBytes("GBK");
byte[] outputBytes = new byte[256];
while (true) {
try {
cypheredBytes = cipher.doFinal(inputBytes, 0,
inputBytes.length, outputBytes, 0);
break;
} catch (ShortBufferException e) {
outputBytes = new byte[outputBytes.length * 2];
}
}
cryptedString = new String(outputBytes, 0, cypheredBytes, "iso-8859-1");
return cryptedString;
}
/**
*
* 解密
* @param sourcebyte
* @return
* @throws InvalidKeyException
* @throws UnsupportedEncodingException
* @throws IllegalStateException
* @throws IllegalBlockSizeException
* @throws BadPaddingException
*/
private String decrypt(byte[] sourcebyte) throws InvalidKeyException,
UnsupportedEncodingException, IllegalStateException,
IllegalBlockSizeException, BadPaddingException{
if(sourcebyte == null || sourcebyte.length == 0){
throw new IllegalBlockSizeException("sourcebyte length equals 0");
}
String cryptedString = null;
int cypheredBytes = 0;
byte[] inputBytes = sourcebyte;
byte[] outputBytes = new byte[256];
while (true) {
try {
cypheredBytes = cipher.doFinal(inputBytes, 0,
inputBytes.length, outputBytes, 0);
break;
} catch (ShortBufferException e) {
outputBytes = new byte[outputBytes.length * 2];
}
}
cryptedString = new String(outputBytes, 0, cypheredBytes, "GBK");
return cryptedString;
}
public String encrpts(String string) throws InvalidKeyException,
UnsupportedEncodingException, IllegalStateException,
IllegalBlockSizeException, BadPaddingException {
return SimpleCrypto.toHex(encrpt(string));
}
public String decrypts(String string) throws InvalidKeyException,
UnsupportedEncodingException, IllegalStateException,
IllegalBlockSizeException, BadPaddingException, Exception {
return decrypt(SimpleCrypto.toByte(string));
}
/**
* 设置密钥
* @param keyString
*/
private void setKey(String keyString) {
byte[] keyData = keyString.getBytes();
key = new SecretKeySpec(keyData, 0, keyData.length, "DES");
}
private void initDecrypt() throws InvalidKeyException {
cipher.init(Cipher.DECRYPT_MODE, key);
}
private void initEncrypt() throws InvalidKeyException {
cipher.init(Cipher.ENCRYPT_MODE, key);
}
}
注意点:
(1)加密获取实例:DES,因为DES就是:DES/ECB/PKCS5Padding,默认的加密算法
(2)解密获取实例:DES/ECB/NoPadding
(3)加密前,会使用默认的空格填充,解密的时候要去空格。