Android数据安全之DES加密

对称加密算法,加密和解密使用相同密钥的算法。优点:加密速度比较快.可以加密比较大的文件;缺点:密码可以自己指定 ,密码容易泄露

背景

DES(Data Encryption Standard)数据加密标准,DES加密算法出自IBM的研究,后来被美国政府正式采用,之后开始广泛流传,但是近些年使用越来越少,因为DES使用56位密钥,以现代计算能力,24小时内即可被破解。

算法原理

涉及到多种数学运算,内容相对晦涩难懂,网上也有很多相关的算法解析,在这里重点学习如何使用,所有就不多赘述了。

DES代码实现

1)相关常量类介绍
private static final String TAG = DESUtils.class.getSimpleName();
private final static String HEX = "0123456789ABCDEF";
private final static String TRANSFORMATION = "DES/CBC/PKCS5Padding";//DES是加密方式 CBC是工作模式 PKCS5Padding是填充模式
private final static String IVPARAMETERSPEC = "01020304";//初始化向量参数,AES 为16bytes. DES 为8bytes.
private final static String DES = "DES";//DES是加密方式
private static final String SHA1PRNG = "SHA1PRNG";// SHA1PRNG 强随机种子算法, 要区别4.2以上版本的调用方法
2)动态生成秘钥(即生成一个随机Key的方法)
/**
* 动态生成密钥
* @return 生成随机数,可以当做动态的密钥 加密和解密的密钥必须一致,不然将不能解密
*/
public static String generateKey() {

   try {
       SecureRandom secureRandom = SecureRandom.getInstance(SHA1PRNG,"Crypto");
       byte[] bytesKey = new byte[20];// 长度不能够小于8位字节 因为DES固定格式为64bits,即8bytes。
       secureRandom.nextBytes(bytesKey);
       String strKey = toHexString(bytesKey);
       return strKey;
   } catch (Exception e) {
       e.printStackTrace();
   }
   return null;
}
3)处理秘钥Key(转换密钥)的两种方式
/**
 * 密钥处理方式  转换密钥(包括可以做随机处理)方式一 (针对DES)
 */
private static Key getRawKeyMethodOne(String key) throws Exception {
    DESKeySpec dks = new DESKeySpec(key.getBytes());
    SecretKeyFactory keyFactory = SecretKeyFactory.getInstance(DES);
    return keyFactory.generateSecret(dks);
}

/**
 *  密钥处理方式 转换密钥(包括可以做随机处理)方式二 (同时适用于其他对称加密算法)
 */
private static Key getRawKeyMethodTwo(String key) throws Exception {
    KeyGenerator kgen = KeyGenerator.getInstance(DES);
    //for android
    SecureRandom sr = SecureRandom.getInstance(SHA1PRNG, "Crypto");
    // for Java
    // secureRandom sr = SecureRandom.getInstance(SHA1PRNG);
    sr.setSeed(key.getBytes());
    kgen.init(64, sr); //DES固定格式为64bits,即8bytes。
    SecretKey skey = kgen.generateKey();
    byte[] raw = skey.getEncoded();
    return new SecretKeySpec(raw, DES);//核心代码,前面都是对key进行处理,如果这个key之前就做过处理,只需这一步即可
}
4)加密实现
public static String encrypt(String key, String data) {
     return encrypt(key, data.getBytes());
 }

 /**
  * DES算法,加密
  *
  * @param data 待加密字符串
  * @param key  加密私钥,长度不能够小于8位
  * @return 加密后的字节数组,一般结合Base64编码使用
  */
 public static String encrypt(String key, byte[] data) {
     try {
         Cipher cipher = Cipher.getInstance(TRANSFORMATION);
         IvParameterSpec iv = new IvParameterSpec(IVPARAMETERSPEC.getBytes());
         cipher.init(Cipher.ENCRYPT_MODE, getRawKeyMethodOne(key), iv);
         byte[] bytes = cipher.doFinal(data);
         return Base64.encodeToString(bytes, Base64.DEFAULT);
     } catch (Exception e) {
         return null;
     }
 }
5)解密实现
/**
  * DES算法,解密 获取编码后的值
  */
 public static String decrypt(String key, String data) {
     return decrypt(key, Base64.decode(data, Base64.DEFAULT));
 }

 /**
  * DES算法,解密
  * @param data 待解密字符串
  * @param key  解密私钥,长度不能够小于8位
  * @return 解密后的字节数组
  */
 public static String decrypt(String key, byte[] data) {
     try {
         Cipher cipher = Cipher.getInstance(TRANSFORMATION);
         IvParameterSpec iv = new IvParameterSpec(IVPARAMETERSPEC.getBytes());
         cipher.init(Cipher.DECRYPT_MODE, getRawKeyMethodOne(key), iv);
         byte[] original = cipher.doFinal(data);
         return new String(original);
     } catch (Exception e) {
         Log.d("TAG:"+TAG,"-------DES解码密码错误-------");
         return null;
     }
 }
6)二进制转(16进制)字符串
/**
     * 二进制转(16进制)字符串
     */
    private static String ByteToHex(byte[] bytesKey) {
        if (bytesKey == null)
            return "";
        StringBuilder sb = new StringBuilder();
        for (byte b : bytesKey) {
            sb.append(HEX.charAt((b >> 4) & 0x0f)).append(HEX.charAt(b & 0x0f));
        }
        return sb.toString();
    }
7)测试
private String data = "这是一个测试编码和加解密的字符串数据";
private String DES_Key = "deskey";
private boolean isDesEncrypt = true;

/**
 * DES 加解密
 */
private void desEncrypt() {

    tvContent.setText("");
    if (isDesEncrypt) {
        encryptDES = DESUtils.encrypt(DES_Key, data);
        Log.d("TAG:" + TAG, "----DES加密后: " + encryptDES);
        tvContent.setText("DES加密后: " + encryptDES);
    } else {
        String decodeDES = DESUtils.decrypt(DES_Key, encryptDES);
        Log.d("TAG:" + TAG, "----DES解密后: " + decodeDES);
        tvContent.setText("DES解密后: " + decodeDES);
    }

    isDesEncrypt = !isDesEncrypt;
}

追及

完整代码参考github:Android-Encrypt-master

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值