在使用HTTP协议传输文本,接入第三方接口时,同时需要一个验签环节,在数据库密码入库是也需要一个加密环节,为了提高安全性,可以采用BASE64加盐后再进行加密的算法。
如果是验签,双方约定一个共同的盐值,针对要传输的字符串进行BASE64加盐加密,再对MD5进行加盐加密,即可保证安全性。
3.1 base64加密工具类
import com.lianqian.urs.common.enums.SignTypeEnum;
import com.lianqian.urs.common.exception.ServiceException;
import org.apache.commons.codec.binary.Base64;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.UnsupportedEncodingException;
public class ArgsSignUtil {
private static final Logger LOGGER = LoggerFactory.getLogger(ArgsSignUtil.class);
/**
* 待签名字符串等号符
*/
@SuppressWarnings("unused")
private static final String SIGN_EQUAL_CHAR = "=";
/**
* 待签名字符串键值对连接符
*/
@SuppressWarnings("unused")
private static final String SIGN_JOINER_CHAR = "&";
/**
* @Description: 验证签名
*/
public static boolean checkArgsSignByType(SignTypeEnum signType, String inputJons, String signKey, String sign) {
try {
String strToSign = genStrToSignByArgsJsonAndCid(inputJons, signKey, signType);
// rsa签名
if (SignTypeEnum.RSA.equals(signType)) {
LOGGER.debug("sign:" + sign);
LOGGER.debug("checksign-key:" + signKey);
return RSAAndDESUtils.verify(strToSign.getBytes("UTF-8"), signKey, sign.getBytes("UTF-8"));
} else if (SignTypeEnum.MD5.equals(signType)) {// md5签名(默认md5签名,非rsa签名即为md5签名)
String md5Sign = MessageDigest5.encrypt(strToSign, "UTF-8");
LOGGER.debug("接口请求md5签名:" + sign);
LOGGER.debug("待md5签名字符串:" + strToSign);
LOGGER.debug("生成请求md5签名:" + md5Sign);
return sign.equalsIgnoreCase(md5Sign);
} else {
return false;
}
} catch (Exception e) {
LOGGER.error("验签失败:signType-{},data-{},signKey-{},sign-{}", signType, inputJons, signKey, sign, e);
}
return false;
}
public static boolean checkOpenApiSignByType(SignTypeEnum signType, String inputJson, String signKey, String sign) {
try {
String strToSign = genStrToSignForOpenApi(inputJson, signKey, signType);
// rsa签名
if (SignTypeEnum.RSA.equals(signType)) {
LOGGER.debug("三方签名:" + sign);
LOGGER.debug("签名公钥:" + signKey);
return RSAAndDESUtils.doCheck(strToSign, sign, signKey);
} else if (SignTypeEnum.MD5.equals(signType)) {
String md5Sign = MessageDigest5.encrypt(strToSign, "UTF-8");
LOGGER.debug("三方签名:" + sign);
LOGGER.debug("待md5签名字符串:" + strToSign);
LOGGER.debug("生成请求md5签名:" + md5Sign);
return sign.equalsIgnoreCase(md5Sign);
} else {
return false;
}
} catch (Exception e) {
LOGGER.error("验签失败:signType-{},data-{},signKey-{},sign-{}", signType, inputJson, signKey, sign, e);
}
return false;
}
/**
* @Description: 生成待签名的字符串
* @Author: panjl
* @Since: 2014年11月5日上午11:18:45
* @param inputJson
* 业务参数json串
* @param md5Key
* 渠道签名key
* @param signType
* @return
*/
private static String genStrToSignByArgsJsonAndCid(String inputJson, String md5Key, SignTypeEnum signType) {
// 拼接要生成签名的字符串
StringBuilder strToSign = new StringBuilder();
strToSign.append(inputJson);
if (SignTypeEnum.MD5.equals(signType)) {
// 添加渠道md5签名key
strToSign.append(md5Key);
}
String result = strToSign.toString();
LOGGER.debug("生成待签名字符串0为:" + result);
return result;
}
public static String genStrToSignForOpenApi(String inputJson, String md5Key, SignTypeEnum signType) {
StringBuilder strToSign = new StringBuilder();
strToSign.append(inputJson);
if (SignTypeEnum.MD5.equals(signType)) {
strToSign.append(Base64.encodeBase64String(inputJson.getBytes()));
strToSign.append(md5Key);
}
String result = strToSign.toString();
LOGGER.debug("生成待签名字符串为:" + result);
return result;
}
/**
* @Description: 根据签名类型生成签名
*/
public static String genSignByType(SignTypeEnum signType, String input, String signKey) throws UnsupportedEncodingException {
try {
String result = "";
String strToSign = genStrToSignByArgsJsonAndCid(input, signKey, signType);
if (SignTypeEnum.RSA.equals(signType)) {
result = RSAAndDESUtils.sign(strToSign.getBytes("UTF-8"), signKey);
//result = URLEncoder.encode(result, "UTF-8");
} else if (SignTypeEnum.MD5.equals(signType)) {
result = MessageDigest5.encrypt(strToSign, "UTF-8");
}
LOGGER.debug("sign-key:" + signKey);
LOGGER.debug("生成签名:" + result);
return result;
} catch (RuntimeException e) {
e.printStackTrace();
return "";
} catch (Exception e) {
throw new ServiceException(Constant.FAILED_OTHERS, "签名生成失败");
}
}
}
加密类型的枚举类
public enum SignTypeEnum {
MD5("MD5", 1, "MD5签名"), RSA("RSA", 10, "RSA签名");
private String code;
private Integer index;
private String desc;
private SignTypeEnum(String code, Integer index, String desc) {
this.code = code;
this.index = index;
this.desc = desc;
}
/**
* @Description: 获取默认的签名类型
*/
public static SignTypeEnum getDefaultSignType() {
return SignTypeEnum.MD5;
}
/**
* @Description: 根据签名类型码获取签名类型
* @Author: panjl
* @Since: 2014年11月26日上午10:12:28
* @param code
* @return
*/
public static SignTypeEnum getByCode(String code) {
SignTypeEnum ret = null;
for (SignTypeEnum signType : SignTypeEnum.values()) {
if (signType.getCode().equals(code)) {
ret = signType;
break;
}
}
return ret;
}
public String getCode() {
return code;
}
public void setCode(String code) {
this.code = code;
}
public String getDesc() {
return desc;
}
public void setDesc(String desc) {
this.desc = desc;
}
/**
* @return the index
*/
public Integer getIndex() {
return index;
}
/**
* @param index
* the index to set
*/
public void setIndex(Integer index) {
this.index = index;
}
}
public class MessageDigest5 {
public static String encrypt(String input) throws NoSuchAlgorithmException {
MessageDigest msgDigest = MessageDigest.getInstance("MD5");
msgDigest.update(input.getBytes());
return byteToHex(msgDigest.digest());
}
public static String encrypt(String input, String charset) throws NoSuchAlgorithmException, UnsupportedEncodingException {
MessageDigest msgDigest = MessageDigest.getInstance("MD5");
msgDigest.update(input.getBytes(charset));
return byteToHex(msgDigest.digest());
}
public static String byteToHex(byte[] b) {
StringBuffer sBuffer = new StringBuffer();
for (int i = 0; i < b.length; i++) {
String sTemp = Integer.toHexString(b[i] & 0xFF);
if (sTemp.length() == 1)
sBuffer.append("0");
sBuffer.append(sTemp);
}
return sBuffer.toString();
}
public static void main(String[] args) throws NoSuchAlgorithmException, UnsupportedEncodingException {
System.out.println(encrypt("{\"DomainOrderId\":\"nqDEvnInprf4WeYJrwt3gOBhdBFRey2o\",\"PolicyholderName\":\"托尔斯\",\"Birthday\":\"1987-09-09\",\"Mobile\":\"13438970025\"}ltdj_key", "UTF-8"));
}
}
3.3 调用方法
String blackUserJson = JSON.toJSONString(blackUserRecord);
String strToSign = ArgsSignUtil.genStrToSignForOpenApi(blackUserJson, Constant.BLACKUSER_MD5_KEY,
SignTypeEnum.getByCode(blackUserReq.getSignType()));
String md5Sign = MessageDigest5.encrypt(strToSign, Constant.ENCOD_CHARSET_UTF8);