一、对称加密算法
DES
- 3DES
AES
PBE
IDEA
对称加密算法为初等加密算法,安全性相对不高。
二、对称加密算法-DES
1、理论知识
DES(Data Encryption Standard)数据加密标准:
密钥长度 | 默认 | 工作模式 | 填充方式 | 实现方 |
---|---|---|---|---|
56 | 56 | ECB、CBC、PCBC、CTR、CTS、CFB、CFB8到128、OFB、OFB8到128 | NoPadding、PKCS5Padding、ISO10126Padding | JDK |
64 | 56 | 同上 | PKCS7Padding、ISO10126d2Padding、X932Padding、ISO7816d4Padding、ZeroBytePadding | BC |
2、JDK 实现:
public static void jdkDES() throws NoSuchAlgorithmException, InvalidKeyException, InvalidKeySpecException, NoSuchPaddingException, BadPaddingException, IllegalBlockSizeException, DecoderException {
String src = "test source";
// 生成KEY
KeyGenerator keyGenerator = KeyGenerator.getInstance("DES");
keyGenerator.init(56);
// 根据指定算法生成默认长度的密钥
// keyGenerator.init(new SecureRandom());
System.out.println(keyGenerator.getProvider());
Key key = keyGenerator.generateKey();
byte[] keyBytes = key.getEncoded();
// KEY转换
KeySpec desKeySpec = new DESKeySpec(keyBytes);
SecretKeyFactory factory = SecretKeyFactory.getInstance("DES");
System.out.println(factory.getProvider());
Key convertKey = factory.generateSecret(desKeySpec);
// 加密
Cipher enCipher = Cipher.getInstance("DES/ECB/PKCS5Padding");
enCipher.init(Cipher.ENCRYPT_MODE, convertKey);
byte[] encode = enCipher.doFinal(src.getBytes());
// Hex 编码
String encodeHex = Hex.encodeHexString(encode);
System.out.println(enCipher.getProvider() + "- des encrypt(Hex):" + encodeHex);
// Base64 编码
String encodeBase64 = Base64.encodeBase64String(encode);
System.out.println(enCipher.getProvider() + "- des encrypt(Base64):" + encodeBase64);
// 解密
Cipher deCipher = Cipher.getInstance("DES/ECB/PKCS5Padding");
deCipher.init(Cipher.DECRYPT_MODE, convertKey);
byte[] decode = deCipher.doFinal(encode);
// byte[] decode = deCipher.doFinal(Hex.decodeHex(encodeHex));
// byte[] decode = deCipher.doFinal(Base64.decodeBase64(encodeBase64));
System.out.println(deCipher.getProvider() + "- des decrypt:" + new String(decode));
}
3、Bouncy Castle 实现:
public static void bcDES() throws NoSuchProviderException, NoSuchAlgorithmException, InvalidKeyException, InvalidKeySpecException, NoSuchPaddingException, BadPaddingException, IllegalBlockSizeException {
String src = "test source";
// 设置 BC 的提供Provider
Security.addProvider(new BouncyCastleProvider());
// 生成KEY
KeyGenerator keyGenerator = KeyGenerator.getInstance("DES","BC");
keyGenerator.init(56);
// 根据指定算法生成默认长度的密钥
// keyGenerator.init(new SecureRandom());
System.out.println(keyGenerator.getProvider());
Key key = keyGenerator.generateKey();
byte[] keyBytes = key.getEncoded();
// KEY转换
KeySpec desKeySpec = new DESKeySpec(keyBytes);
SecretKeyFactory factory = SecretKeyFactory.getInstance("DES","BC");
System.out.println(factory.getProvider());
Key convertKey = factory.generateSecret(desKeySpec);
// 加密
Cipher enCipher = Cipher.getInstance("DES/ECB/PKCS5Padding","BC");
enCipher.init(Cipher.ENCRYPT_MODE, convertKey);
byte[] encode = enCipher.doFinal(src.getBytes());
// Hex 编码
String encodeHex = Hex.encodeHexString(encode);
System.out.println(enCipher.getProvider() + "- des encrypt(Hex):" + encodeHex);
// Base64 编码
String encodeBase64 = Base64.encodeBase64String(encode);
System.out.println(enCipher.getProvider() + "- des encrypt(Base64):" + encodeBase64);
// 解密
Cipher deCipher = Cipher.getInstance("DES/ECB/PKCS5Padding","BC");
deCipher.init(Cipher.DECRYPT_MODE, convertKey);
byte[] decode = deCipher.doFinal(encode);
// byte[] decode = deCipher.doFinal(Hex.decodeHex(encodeHex));
// byte[] decode = deCipher.doFinal(Base64.decodeBase64(encodeBase64));
System.out.println(deCipher.getProvider() + "- des decrypt: " + new String(decode));
}
三、对称加密算法-3重DES
1、理论知识
出现缘由:
1、DES违反柯克霍夫原则
2、安全问题(怀疑存在后门)
3重DES的好处:
1、密钥长度增强
2、迭代次数提高
3、3重DES的应用十分广泛
密钥长度 | 默认 | 工作模式 | 填充方式 | 实现方 |
---|---|---|---|---|
112、168 | 168 | ECB、CBC、PCBC、CTR、CTS、CFB、CFB8到128、OFB、OFB8到128 | Nopadding、PKCS5Padding、ISO10126Padding | JDK |
168、192 | 168 | 同上 | PKCS7Padding、ISO10126d2Padding、X932Padding、ISO7816d4Padding、ZeroBytePadding | BC |
2、JDK 实现:
public static void jdk3DES() throws NoSuchAlgorithmException, InvalidKeyException, InvalidKeySpecException, NoSuchPaddingException, BadPaddingException, IllegalBlockSizeException {
String src = "test source";
// 生成KEY
KeyGenerator keyGenerator = KeyGenerator.getInstance("DESede");
keyGenerator.init(168);
// 根据指定算法生成默认长度的密钥
// keyGenerator.init(new SecureRandom());
System.out.println(keyGenerator.getProvider());
Key key = keyGenerator.generateKey();
byte[] keyBytes = key.getEncoded();
// KEY转换
KeySpec desKeySpec = new DESedeKeySpec(keyBytes);
SecretKeyFactory factory = SecretKeyFactory.getInstance("DESede");
System.out.println(factory.getProvider());
Key convertKey = factory.generateSecret(desKeySpec);
// 加密
Cipher enCipher = Cipher.getInstance("DESede/ECB/PKCS5Padding");
enCipher.init(Cipher.ENCRYPT_MODE, convertKey);
byte[] encode = enCipher.doFinal(src.getBytes());
// Hex 编码
String encodeHex = Hex.encodeHexString(encode);
System.out.println(enCipher.getProvider() + "- 3des encrypt(Hex): " + encodeHex);
// Base64 编码
String encodeBase64 = Base64.encodeBase64String(encode);
System.out.println(enCipher.getProvider() + "- 3des encrypt(Base64): " + encodeBase64);
// 解密
Cipher deCipher = Cipher.getInstance("DESede/ECB/PKCS5Padding");
deCipher.init(Cipher.DECRYPT_MODE, convertKey);
byte[] decode = deCipher.doFinal(encode);
// byte[] decode = deCipher.doFinal(Hex.decodeHex(encodeHex));
// byte[] decode = deCipher.doFinal(Base64.decodeBase64(encodeBase64));
System.out.println(deCipher.getProvider() + "- 3des decrypt: " + new String(decode));
}
3、Bouncy Castle 实现:
public static void bc3DES() throws NoSuchProviderException, NoSuchAlgorithmException, InvalidKeyException, InvalidKeySpecException, NoSuchPaddingException, BadPaddingException, IllegalBlockSizeException {
String src = "test source";
// 设置 BC 的提供Provider
Security.addProvider(new BouncyCastleProvider());
// 生成KEY
KeyGenerator keyGenerator = KeyGenerator.getInstance("DESede","BC");
keyGenerator.init(168);
// 根据指定算法生成默认长度的密钥
// keyGenerator.init(new SecureRandom());
System.out.println(keyGenerator.getProvider());
Key key = keyGenerator.generateKey();
byte[] bytesKey = key.getEncoded();
// KEY转换
KeySpec desKeySpec = new DESedeKeySpec(bytesKey);
SecretKeyFactory factory = SecretKeyFactory.getInstance("DESede","BC");
System.out.println(factory.getProvider());
Key convertKey = factory.generateSecret(desKeySpec);
// 加密
Cipher enCipher = Cipher.getInstance("DESede/ECB/PKCS5Padding","BC");
enCipher.init(Cipher.ENCRYPT_MODE, convertKey);
byte[] encode = enCipher.doFinal(src.getBytes());
// Hex 编码
String encodeHex = Hex.encodeHexString(encode);
System.out.println(enCipher.getProvider() + "- 3des encrypt(Hex): " + encodeHex);
// Base64 编码
String encodeBase64 = Base64.encodeBase64String(encode);
System.out.println(enCipher.getProvider() + "- 3des encrypt(Base64): " + encodeBase64);
// 解密
Cipher deCipher = Cipher.getInstance("DESede/ECB/PKCS5Padding","BC");
deCipher.init(Cipher.DECRYPT_MODE, convertKey);
byte[] decode = deCipher.doFinal(encode);
// byte[] decode = deCipher.doFinal(Hex.decodeHex(encodeHex));
// byte[] decode = deCipher.doFinal(Base64.decodeBase64(encodeBase64));
System.out.println(deCipher.getProvider() + " - 3des decrypt: " + new String(decode));
}
四、对称加密算法-AES
1、理论知识
加解密效率高,DES替代者:
AES是目前使用最多的对称加密算法;
AES的优势之一是至今尚未被破解;
AES通常用于移动通信系统加密以及基于SSH协议的软件(SSH Client、secureCRT);
密钥长度 | 默认 | 工作模式 | 填充方式 | 实现方 |
---|---|---|---|---|
128、192、256 | 128 | ECB、CBC、PCBC、CTR、CTS、CFB、CFB8到128、OFB、OFB8到128 | Nopadding、PKCS5Padding、ISO10126Padding | JDK(256位密钥需要获得无政策限制权限文件) |
同上 | 同上 | 同上 | PKCS7Padding、ZeroBytePadding | BC |
无政策限制权限文件是指,因为某些国家的进口管制限制,Java发布的运行环境包中的加解密有一定的限制。
2、JDK 实现:
public static void jdkAES() throws NoSuchAlgorithmException, NoSuchPaddingException, InvalidKeyException, BadPaddingException, IllegalBlockSizeException, DecoderException {
String src = "test source";
// 生成KEY
KeyGenerator keyGenerator = KeyGenerator.getInstance("AES");
keyGenerator.init(128);
// 根据指定算法生成默认长度的密钥
// keyGenerator.init(new SecureRandom());
System.out.println(keyGenerator.getProvider());
Key key = keyGenerator.generateKey();
byte[] keyBytes = key.getEncoded();
// KEY转换
Key convertKey = new SecretKeySpec(keyBytes, "AES");
// 加密
Cipher enCipher = Cipher.getInstance("AES/ECB/PKCS5Padding");
enCipher.init(Cipher.ENCRYPT_MODE, convertKey);
byte[] encode = enCipher.doFinal(src.getBytes());
// Hex 编码
String encodeHex = Hex.encodeHexString(encode);
System.out.println(enCipher.getProvider() + "- aes encrypt(Hex):" + encodeHex);
// Base64 编码
String encodeBase64 = Base64.encodeBase64String(encode);
System.out.println(enCipher.getProvider() + "- aes encrypt(Base64):" + encodeBase64);
// 解密
Cipher deCipher = Cipher.getInstance("AES/ECB/PKCS5Padding");
deCipher.init(Cipher.DECRYPT_MODE, convertKey);
byte[] decode = deCipher.doFinal(encode);
// byte[] decode = deCipher.doFinal(Hex.decodeHex(encodeHex));
// byte[] decode = deCipher.doFinal(Base64.decodeBase64(encodeBase64));
System.out.println(deCipher.getProvider() + "- aes decrypt:" + new String(decode));
}
3、Bouncy Castle 实现:
public static void bcAES() throws NoSuchProviderException, NoSuchAlgorithmException, NoSuchPaddingException, InvalidKeyException, BadPaddingException, IllegalBlockSizeException {
String src = "test source";
// 设置 BC 的提供Provider
Security.addProvider(new BouncyCastleProvider());
// 生成KEY
KeyGenerator keyGenerator = KeyGenerator.getInstance("AES","BC");
keyGenerator.init(128);
// 根据指定算法生成默认长度的密钥
// keyGenerator.init(new SecureRandom());
System.out.println(keyGenerator.getProvider());
Key key = keyGenerator.generateKey();
byte[] keyBytes = key.getEncoded();
// KEY转换
Key convertKey = new SecretKeySpec(keyBytes, "AES");
// 加密
Cipher enCipher = Cipher.getInstance("AES/ECB/PKCS5Padding","BC");
enCipher.init(Cipher.ENCRYPT_MODE, convertKey);
byte[] encode = enCipher.doFinal(src.getBytes());
// Hex 编码
String encodeHex = Hex.encodeHexString(encode);
System.out.println(enCipher.getProvider() + "- aes encrypt(Hex):" + encodeHex);
// Base64 编码
String encodeBase64 = Base64.encodeBase64String(encode);
System.out.println(enCipher.getProvider() + "- aes encrypt(Base64):" + encodeBase64);
// 解密
Cipher deCipher = Cipher.getInstance("AES/ECB/PKCS5Padding","BC");
deCipher.init(Cipher.DECRYPT_MODE, convertKey);
byte[] decode = deCipher.doFinal(encode);
// byte[] decode = deCipher.doFinal(Hex.decodeHex(encodeHex));
// byte[] decode = deCipher.doFinal(Base64.decodeBase64(encodeBase64));
System.out.println(deCipher.getProvider() + "- aes decrypt:" + new String(decode));
}
五、对称加密算法-PBE
1、理论知识
PBE 不是一种全新的算法,而是对现有已有的算法的整合封装:
AES、DES和3重DES在使用上比较一致;
PBE算法结合了消息摘要算法和对称加密算法的优点;
BPE(Password Based Encrytion)基于口令加密(加盐);
算法 | 密钥长度 | 默认 | 工作模式 | 填充方式 | 实现方 |
---|---|---|---|---|---|
PBEWithMD5AndDES | 56 | 56 | CBC | PKCS5Padding | JDK |
PBEWithMD5AndTripleDES | 112、168 | 168 | 同上 | 同上 | 同上 |
PBEWithSHA1AndDESede | 112、168 | 168 | 同上 | 同上 | 同上 |
PBEWithSHA1AndRC2_40 | 40~1024(8倍数) | 128 | 同上 | 同上 | 同上 |
PBEWithMD5AndDES | 64 | 64 | CBC | PKCS5Padding、PKCS7Padding、ISO10126Padding、ZeroBytePadding | BC |
PBEWithMD5AndRC2 | 128 | 128 | 同上 | 同上 | 同上 |
PBEWithSHA1AndDES | 64 | 64 | 同上 | 同上 | 同上 |
PBEWithSHA1AndRC2 | 128 | 128 | 同上 | 同上 | 同上 |
PBEWithSHAAndIDEA-CBC | 128 | 128 | 同上 | 同上 | 同上 |
PBEWithSHAAnd2-KeyTripleDES-CBC | 128 | 128 | 同上 | 同上 | 同上 |
PBEWithSHAAnd3-KeyTripleDES-CBC | 192 | 192 | 同上 | 同上 | 同上 |
2、JDK 实现:
public static void jdkPBE() throws NoSuchAlgorithmException, InvalidKeySpecException, NoSuchPaddingException, InvalidAlgorithmParameterException, InvalidKeyException, BadPaddingException, IllegalBlockSizeException {
String src = "test source";
// 初始化盐
SecureRandom random = new SecureRandom();
byte[] salt = random.generateSeed(8);
PBEParameterSpec pbeParameterSpec = new PBEParameterSpec(salt, 100);
// 口令与密码
String password = "imooc";
PBEKeySpec pbeKeySpec = new PBEKeySpec(password.toCharArray());
SecretKeyFactory factory = SecretKeyFactory.getInstance("PBEWithMD5AndDES");
Key key = factory.generateSecret(pbeKeySpec);
// 加密
Cipher enCipher = Cipher.getInstance("PBEWithMD5AndDES");
enCipher.init(Cipher.ENCRYPT_MODE, key, pbeParameterSpec);
byte[] encode = enCipher.doFinal(src.getBytes());
// Hex 编码
String encodeHex = Hex.encodeHexString(encode);
System.out.println(enCipher.getProvider() + "- pbe encrypt(Hex):" + encodeHex);
// Base64 编码
String encodeBase64 = Base64.encodeBase64String(encode);
System.out.println(enCipher.getProvider() + "- pbe encrypt(Base64):" + encodeBase64);
// 解密
Cipher deCipher = Cipher.getInstance("PBEWithMD5AndDES");
deCipher.init(Cipher.DECRYPT_MODE, key, pbeParameterSpec);
byte[] decode = deCipher.doFinal(encode);
// byte[] decode = deCipher.doFinal(Hex.decodeHex(encodeHex));
// byte[] decode = deCipher.doFinal(Base64.decodeBase64(encodeBase64));
System.out.println(deCipher.getProvider() + "- pbe decrypt:" + new String(decode));
}
3、Bouncy Castle 实现:
public static void bcPBE() throws NoSuchAlgorithmException, InvalidKeySpecException, NoSuchProviderException, NoSuchPaddingException, InvalidAlgorithmParameterException, InvalidKeyException, BadPaddingException, IllegalBlockSizeException {
String src = "test source";
// 设置 BC 的提供Provider
Security.addProvider(new BouncyCastleProvider());
// 初始化盐
SecureRandom random = new SecureRandom();
byte[] salt = random.generateSeed(8);
PBEParameterSpec pbeParameterSpec = new PBEParameterSpec(salt, 100);
// 口令与密码
String password = "imooc";
PBEKeySpec pbeKeySpec = new PBEKeySpec(password.toCharArray());
SecretKeyFactory factory = SecretKeyFactory.getInstance("PBEWithMD5AndDES","BC");
Key key = factory.generateSecret(pbeKeySpec);
// 加密
Cipher enCipher = Cipher.getInstance("PBEWithMD5AndDES","BC");
enCipher.init(Cipher.ENCRYPT_MODE, key, pbeParameterSpec);
byte[] encode = enCipher.doFinal(src.getBytes());
// Hex 编码
String encodeHex = Hex.encodeHexString(encode);
System.out.println(enCipher.getProvider() + "- pbe encrypt(Hex):" + encodeHex);
// Base64 编码
String encodeBase64 = Base64.encodeBase64String(encode);
System.out.println(enCipher.getProvider() + "- pbe encrypt(Base64):" + encodeBase64);
// 解密
Cipher deCipher = Cipher.getInstance("PBEWithMD5AndDES","BC");
deCipher.init(Cipher.DECRYPT_MODE, key, pbeParameterSpec);
byte[] decode = deCipher.doFinal(encode);
// byte[] decode = deCipher.doFinal(Hex.decodeHex(encodeHex));
// byte[] decode = deCipher.doFinal(Base64.decodeBase64(encodeBase64));
System.out.println(deCipher.getProvider() + "- pbe decrypt:" + new String(decode));
}
六、其它
当加密和解密不在同一方时:
把密钥特殊处理后发给对方;
双方约定密钥;
主要知识点来源于慕课慕课网上 moocer老师 提供的 java 加密系列教程。 原创不易,如需转载,请标明出处!
最后修改:2019-10-12 11:28:27
© 著作权归作者所有
如果觉得我的文章对你有用,请随意赞赏
扫一扫支付

发表评论