DES 密钥生成 加密解密

import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
import java.security.spec.InvalidKeySpecException;

import javax.crypto.BadPaddingException;
import javax.crypto.Cipher;
import javax.crypto.IllegalBlockSizeException;
import javax.crypto.NoSuchPaddingException;
import javax.crypto.SecretKey;
import javax.crypto.SecretKeyFactory;
import javax.crypto.spec.DESKeySpec;

public class DESTool {

    /**
     * 方法描述:一重解密
     *
     * @param keySeed 字节数组类型的密钥种子的字节
     * @param decryptData 字节数组类型的待解密的数据
     * @return 返回解密结果
     */
    public static byte[] decrypt(byte[] keySeed,byte[] decryptData){
        return encryptOrDecrypt(Cipher.DECRYPT_MODE, keySeed, decryptData);
    }

    /**
     * 方法描述:一重加密
     *
     * @param keySeed 字节数组类型的密钥种子的字节
     * @param encryptData 字节数组类型的待加密的数据
     * @return 返回加密结果
     */
    public static byte[] encrypt(byte[] keySeed,byte[] encryptData){
        return encryptOrDecrypt(Cipher.ENCRYPT_MODE, keySeed, encryptData);
    }

    /**
     *
     * @param firstKeySeed 最内层字节数组类型的密钥种子的字节
     * @param secondKeySeed 中间层字节数组类型的密钥种子的字节
     * @param thirdKeySeed 最外层字节数组类型的密钥种子的字节
     * @param encryptData 字节数组类型的待加密的数据
     * @return 返回加密结果
     */
    public static byte[] threeEncrypt(byte[] firstKeySeed, byte[] secondKeySeed,
                               byte[] thirdKeySeed, byte[] encryptData){
        return encrypt(thirdKeySeed,
                encrypt(secondKeySeed,
                        encrypt(firstKeySeed, encryptData)));
    }

    /**
     *
     * @param firstKeySeed 最内层字节数组类型的密钥种子的字节
     * @param secondKeySeed 中间层字节数组类型的密钥种子的字节
     * @param thirdKeySeed 最外层字节数组类型的密钥种子的字节
     * @param decryptData 字节数组类型的待解密的数据
     * @return 返回解密结果
     */
    public static byte[] threeDecrypt(byte[] firstKeySeed, byte[] secondKeySeed,
                               byte[] thirdKeySeed, byte[] decryptData){
        return decrypt(firstKeySeed,
                decrypt(secondKeySeed,
                        decrypt(thirdKeySeed, decryptData)));
    }

    /**
     * 方法描述:DES加密和解密的核心工具
     *
     * @param keySeed 字节数组类型的密钥种子的字节    相同字节数组类型的密钥种子可以生成相同的密钥
     *                所以当密钥种子编码(Base64、utf-8、utf-16等)为字符串后,需要记住编码方式,
     *                  以便于以后可以根据对应的解码方式再次获得密钥种子的字节数组类型的数据
     * @param encryptData 字节数组类型的待加密或解密的数据
     * @param encryptOrDecrypt 有两个可选值 Cipher.ENCRYPT_MODE(加密)
     *                         和 Cipher.DECRYPT_MODE(解密)
     * @return 返回加密或解密结果
     */
    private static byte[] encryptOrDecrypt(int encryptOrDecrypt, byte[] keySeed,
                                    byte[] encryptData){
        if (keySeed != null && encryptData != null &&
                (encryptOrDecrypt == Cipher.ENCRYPT_MODE ||
                        encryptOrDecrypt == Cipher.DECRYPT_MODE )){
            SecretKey secretKey = generateKey(keySeed);
            if (secretKey != null){
                try {
                    // 根据参数创建对应算法的 加密解密工具对象
                    Cipher cipher = Cipher.getInstance("DES");
                    // 初始化加密解密工具
                    // 参数一决定了工具是加密还是解密
                    cipher.init(encryptOrDecrypt,secretKey,new SecureRandom());
                    // 开始加密或解密
                    return cipher.doFinal(encryptData);
                } catch (NoSuchAlgorithmException e) {
                    e.printStackTrace(); // 加密解密工具对象 创建失败
                } catch (NoSuchPaddingException e) {
                    e.printStackTrace(); // 加密解密工具对象 创建失败
                } catch (InvalidKeyException e) {
                    e.printStackTrace(); // 加密解密工具对象 初始化失败
                } catch (BadPaddingException e) {
                    e.printStackTrace(); // 加密解密工具运行失败
                } catch (IllegalBlockSizeException e) {
                    e.printStackTrace(); // 加密解密工具运行失败
                }
            }
        }
        return null;
    }

    /**
     * 方法描述:根据密钥种子生成对应的密钥
     *
     * @param keySeed 字节数组类型的密钥种子的字节    相同字节数组类型的密钥种子可以生成相同的密钥
     *                所以当密钥种子编码(Base64、utf-8、utf-16等)为字符串后,需要记住编码方式,
     *                  以便于以后可以根据对应的解码方式再次获得密钥种子的字节数组类型的数据
     * @return 用于DES加密解密的密钥对象
     */
    private static SecretKey generateKey(byte[] keySeed){
        if (keySeed !=null) {
            try {
                // 将密钥种子转为 生成密钥 时需要用到的材料
                DESKeySpec desKeySpec = new DESKeySpec(keySeed);
                // 创建 生成密钥的工厂对象
                SecretKeyFactory secretKeyFactory = SecretKeyFactory.getInstance("DES");
                if (secretKeyFactory != null){
                    // 生成密钥
                    return secretKeyFactory.generateSecret(desKeySpec);
                }
            } catch (InvalidKeyException e) {
                e.printStackTrace(); // 密钥种子的字节长度低于8个字节
            } catch (NoSuchAlgorithmException e) {
                e.printStackTrace(); // 生成密钥工厂对象 创建失败
            } catch (InvalidKeySpecException e) {
                e.printStackTrace(); // 生成密钥失败
            }
        }
        return null;
    }
}

你可能感兴趣的:(安全)