AES+base64实现双重加密(二)

上篇文章写到加密工具类,但是要怎么调用呢。而且Java中和Oralce中的加密算法不一样(具体为什么,我没研究,以后再说吧。。),所以以下要讲到在Java后台和oracle中如何使用。

老规矩贴上代码,如何在Java后台进行使用。


1.创建一个自定义类

package com.iwork.platform.typehandler;

import java.io.Serializable;

public class MyString implements Serializable, CharSequence, Comparable<String> {
	
	private static final long serialVersionUID = 1L;
	
	private String value;

	public MyString() {
	}

	public MyString(String value) {
		this.value = value;
	}

	public String getValue() {
		return value;
	}

	public void setValue(String value) {
		this.value = value;
	}

	public int compareTo(String arg0) {
		return 0;
	}

	public char charAt(int arg0) {
		return 0;
	}

	public int length() {
		return value.length();
	}

	public CharSequence subSequence(int arg0, int arg1) {
		return null;
	}

	public String toString() {
		return value;
	}
}


2.自定义转换器

package com.iwork.platform.typehandler;

import java.sql.CallableStatement;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;

import org.apache.ibatis.type.JdbcType;
import org.apache.ibatis.type.TypeHandler;

public class CryptTypeHandler implements TypeHandler<MyString> {
	
	public MyString getResult(ResultSet rs, String columnName) throws SQLException {
		String value = "";
		MyString v = new MyString(value);
		value = rs.getString(columnName);
		if (value != null) {
			// 调用解密方法进行解密
			value = EncryptAndDecrypt.decrypt(value.toString());
			v.setValue(value);
		}
		return v;
	}

	public MyString getResult(ResultSet rs, int columnIndex) throws SQLException {
		String value = "";
		MyString v = new MyString(value);
		value = rs.getString(columnIndex);
		if (value != null) {
			v.setValue(value);
		}
		return v;
	}

	public MyString getResult(CallableStatement cs, int columnIndex) throws SQLException {
		String value = "";
		MyString v = new MyString();
		value = cs.getString(columnIndex);
		if (value != null) {
			v.setValue(value);
		}
		return v;
	}

	public void setParameter(PreparedStatement ps, int i, MyString parameter, JdbcType arg3) throws SQLException {
		String value = "";
		if (parameter != null && parameter.toString() != null) {
			// 调用加密方法进行加密
			value = EncryptAndDecrypt.encrypt(parameter.toString());
		}
		ps.setString(i, value.toString());

	}

}
PS:上述加密解密方法在上篇文章中写到了,自行查看。


3.MyBatis配置

<!-- 自定义类型 --> 
<typeHandlers> 
	<typeHandler javaType="com.iwork.platform.typehandler.MyString" handler="com.iwork.platform.typehandler.CryptTypeHandler"/> 
</typeHandlers>


4.关键步骤了,使用自定义类型

private MyString text;
public MyString getText() {
	return text;
}
public void setText(MyString text) {
	this.text = text;
}

如上text值定义后,在进行增删改查的时候就能直接进行加密解密。


5.最后补充一点,在Mybatis中判断空字符串的问题

<if test="text != null and text.length() > 0"> and text #{text}</if>
直接判断长度就可以了。


文档参考:点击打开链接


我是分割线*****************************************************************************************************************************************************************************


下面开始讲在Oracle中调用此方法

1.创建Java包(加密解密方法和上篇文章讲到的一样)

create or replace and compile java source named encryptanddecrypt as
import java.security.SecureRandom;
import javax.crypto.Cipher;
import javax.crypto.KeyGenerator;
import javax.crypto.spec.SecretKeySpec;
import sun.misc.BASE64Decoder;
import sun.misc.BASE64Encoder;

public class EncryptAndDecrypt
{
	// 加密长度
  private final static int LENGTH = 128;
  // 编码方式
  private final static String ENCODE = "UTF-8";
  // 秘钥
  private final static String defaultKey = "sdit606.";
  // 前缀
  private final static String defaultPrefix = "SDITENCRYPT";

  public static void main(String[] args) {
    String mes = "测试数据";
    String e = encrypt(mes);
    System.out.println("加密后:" + e);
    System.out.println("解密后:" + decrypt(e));
  }

  /**
   * AES加密后再使用BASE64加密
   * 增加前缀
   * 1.辨识正常数据,使其不进行解密
   * 2.提高安全度
   * @param content
   * @return
   * @throws Exception
   */
  public static String encrypt(String content) {
    String value = "";
    try {
      if(!isEmpty(content)){
		value = defaultPrefix + base64Encode(aesEncryptToBytes(content));
	  }
    } catch (Exception e) {
      System.out.println("EncryptAndDecrypt(加密错误)");
      e.printStackTrace();
    }
    return value;
  }

  /**
   * AES解密后再使用BASE64解密
   * 增加前缀
   * 1.辨识正常数据,使其不进行解密
   * 2.提高安全度
   * @param encryptStr
   * @return
   * @throws Exception
   */
  public static String decrypt(String encryptStr) {
    String value = "";
    try {
      int length = defaultPrefix.length();
      if (encryptStr.length() > length) {
        String val = encryptStr.substring(0, length);
        if (val.equals(defaultPrefix)) {
          value = aesDecryptByBytes(base64Decode(encryptStr.substring(length)));
        } else {
          value = encryptStr;
        }
      } else {
        value = encryptStr;
      }
    } catch (Exception e) {
      System.out.println("EncryptAndDecrypt(解密错误)");
      e.printStackTrace();
    }
    return value;
  }

  /**
   * AES加密
   *
   * @param content
   * @return
   * @throws Exception
   */
  public static byte[] aesEncryptToBytes(String content) throws Exception {
    KeyGenerator kgen = KeyGenerator.getInstance("AES");
    kgen.init(LENGTH, new SecureRandom(defaultKey.getBytes()));
    Cipher cipher = Cipher.getInstance("AES");
    SecretKeySpec sks = new SecretKeySpec(kgen.generateKey().getEncoded(), "AES");
    cipher.init(Cipher.ENCRYPT_MODE, sks);
    return cipher.doFinal(content.getBytes(ENCODE));
  }

  /**
   * AES解密
   *
   * @param encryptBytes
   * @return
   * @throws Exception
   */
  public static String aesDecryptByBytes(byte[] encryptBytes) throws Exception {
    KeyGenerator kgen = KeyGenerator.getInstance("AES");
    kgen.init(LENGTH, new SecureRandom(defaultKey.getBytes()));
    Cipher cipher = Cipher.getInstance("AES");
    SecretKeySpec sks = new SecretKeySpec(kgen.generateKey().getEncoded(), "AES");
    cipher.init(Cipher.DECRYPT_MODE, sks);
    byte[] decryptBytes = cipher.doFinal(encryptBytes);
    return new String(decryptBytes);
  }

  /**
   * BASE64 加密
   *
   * @param content
   * @return
   * @throws Exception
   */
  public static String base64Encode(byte[] bytes) {
    return new BASE64Encoder().encode(bytes);
  }

  /**
   * BASE64 解密
   *
   * @param content
   * @return
   * @throws Exception
   */
  public static byte[] base64Decode(String base64Code) throws Exception {
    return isEmpty(base64Code) ? null : new BASE64Decoder().decodeBuffer(base64Code);
  }

  public static boolean isEmpty(String str) {
    return null == str || "".equals(str.trim());
  }
}

2.创建两个函数,使其后续进行调用

create or replace function encrypt(VALUE varchar2)
return varchar2 as
language java name 'EncryptAndDecrypt.encrypt(java.lang.String) return java.lang.String';
/**
 配合EncryptAndDecrypt进行加密
**/

create or replace function decrypt(VALUE varchar2)
return varchar2 as
language java name 'EncryptAndDecrypt.decrypt(java.lang.String) return java.lang.String';
/**
 配合EncryptAndDecrypt进行解密
**/


好了好了,就这样了,懒得测试了。后续再看一下有什么改的吧。。。




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值