android aes加密及gson转化json串时“=”“u003d”
在我们开发项目的时候有时有一些敏感信息需要加密,在加密的方式中我们一般用到的就有两种:一种是非对称加密,一种是对称加密。今天我给大家分享一下对称加密中的AES加密。废话不多说我们直接上代码。
import javax.crypto.Cipher;
import javax.crypto.spec.SecretKeySpec;
//import android.util.Base64;
/**
* @author 针对Android和ios两种方式的加解密方法
* 2017年4月17日上午11:39:00
* SecurityUtil_RSA
*/
public class SecurityUtil_AES {
public static final String AES_SECRET_KEY = "1234567890123456"; // 加密
public static String encrypt(String sSrc, String sKey) throws Exception {
if (sKey == null) {
System.out.print("Key为空null");
return null;
}
// 判断Key是否为16位
if (sKey.length() != 16) {
System.out.print("Key长度不是16位");
return null;
}
byte[] raw = sKey.getBytes("utf-8");
SecretKeySpec skeySpec = new SecretKeySpec(raw, "AES");
Cipher cipher = Cipher.getInstance("AES/ECB/PKCS5Padding");// "算法/模式/补码方式"
cipher.init(Cipher.ENCRYPT_MODE, skeySpec);
byte[] encrypted = cipher.doFinal(sSrc.getBytes());
//return new BASE64Encoder().encode(encrypted);// 此处使用BASE64做转码。
//return new String(Base64.encode(encrypted, Base64.NO_WRAP));// 此处使用BASE64做转码功能,同时能起到2次加密的作用。
return new String(Base64Utils.encode(encrypted));
}
// 解密
public static String decrypt(String sSrc, String sKey) throws Exception {
try {
// 判断Key是否正确
if (sKey == null) {
System.out.print("Key为空null");
return null;
}
// 判断Key是否为16位
if (sKey.length() != 16) {
System.out.print("Key长度不是16位");
return null;
}
byte[] raw = sKey.getBytes("utf-8");
SecretKeySpec skeySpec = new SecretKeySpec(raw, "AES");
Cipher cipher = Cipher.getInstance("AES/ECB/PKCS5Padding");
cipher.init(Cipher.DECRYPT_MODE, skeySpec);
//byte[] encrypted1 = Base64.decode(sSrc,Base64.NO_WRAP);// 先用base64解密
//byte[] encrypted1 = new BASE64Decoder().decodeBuffer(sSrc);// 先用base64解密
byte[] encrypted1 = Base64Utils.decode(sSrc);
try {
byte[] original = cipher.doFinal(encrypted1);
String originalString = new String(original, "utf-8");
return originalString;
} catch (Exception e) {
System.out.println(e.toString());
return null;
}
} catch (Exception ex) {
System.out.println(ex.toString());
return null;
}
}
public static void main(String[] args) throws Exception {
/*
* 此处使用AES-128-ECB加密模式,key需要为16位。
*/
String cKey = "1234567890123456";
// 需要加密的字串
String cSrc = "{\"body\":{\"code\":\"067014\",\"engine\":\"123\",\"imei\":\"867223020015608\",\"lpn\":\"123\",\"mobilePhone\":\"13641300741\",\"name\":\"饭饭\",\"vin\":\"12345678901234567\",\"companyCode\":\"beiqixinnengyuan\",\"username\":\"ryan\"},\"header\":{\"code\":\"R1000\"}}";
System.out.println(cSrc);
// 加密
System.out.println(System.currentTimeMillis());
String enString = SecurityUtil_AES.encrypt(cSrc, cKey);
System.out.println("加密后的字串是:" + enString);
System.out.println(System.currentTimeMillis());
// 解密
String DeString = SecurityUtil_AES.decrypt(enString , cKey);
System.out.println("解密后的字串是:" + DeString);
System.out.println(System.currentTimeMillis());
}
在我们与服务器通讯的时候会把这些加密数据以及未加密的数据转化成json串然后传给服务器,在这个数据转化过程中如果你是用的是Gson的话就要注意了。
String strorder = new Gson().toJson(order);
如果你是以上面这种方式转化的话Gson会把你json数据中的“=”转化为”\u003d”
例如:
k+aOUZw2tm4F/YuzzREq2weJ2mM7Zo+bSJHs2+4gYBat/eBUk6CKt/HnAWxfKfhCg8dGoAX+Tycp5gUpBr92oQqPkCtbGJavLOITBwf+7JU7oqP4dyW95q8MiP5CAUEmoAGj2o0j4dNhY4/FqX2042G+Pseo2ErwrIcnnUO5yHF2SyOeQNRgMAL5gWSc0MhK81ZFI1xs0MlJop9M2n/1U6sg8B8weKJ6+z+IIH0qaec=
会被转化为:
k+aOUZw2tm4F/YuzzREq2weJ2mM7Zo+bSJHs2+4gYBat/eBUk6CKt/HnAWxfKfhCg8dGoAX+Tycp5gUpBr92oQqPkCtbGJavLOITBwf+7JU7oqP4dyW95q8MiP5CAUEmoAGj2o0j4dNhY4/FqX2042G+Pseo2ErwrIcnnUO5yHF2SyOeQNRgMAL5gWSc0MhK81ZFI1xs0MlJop9M2n/1U6sg8B8weKJ6+z+IIH0qaec\u003d
怎么解决这个问题呢我们可以这样初始化gson就可以避免这个问题:
Gson gson = new GsonBuilder().disableHtmlEscaping().create();
String s = gson.toJson(order);
这样我们就可以原汁原味的拿到json串了。
写这篇博客的目的呢!也不是说这个有多难,主要出了这个问题排查了好久都不知道怎么回事,所以在这里总结了一些给自己提个醒,在这里也给大家做一个参考如果有写的不对的地方还请各位提出来共同探讨。