java web传输中的安全签名
说明:
对请求中的数据 Key对进行签名,最终生成一个签名字符串,标记为sign:"djflw8wejwl9w0ejwlush8fw9ew9",位数64位或32位,
服务器端拿到相关数据同样进行签名,与客户端传入的进行比对,如果签名不一致,说明请求数据被篡改,根据业务场景进行相应的拒绝。
/**
* 签名校验
* @param reqMap
* @param key
* @return
*/
public static boolean check(Map<String, Object> reqMap, String key) {
try {
if (null == reqMap || reqMap.isEmpty())
return false;
log.info("--------------req:{}----------------", reqMap);
Collection<String> keyset = reqMap.keySet();
List<String> list = new ArrayList<String>(keyset);
Collections.sort(list);
StringBuffer sb = new StringBuffer();
for (int i = 0; i < list.size(); i++) {
if (!SIGN.equals(list.get(i))) {
Object o = reqMap.get(list.get(i));
if (!ObjectUtils.isEmpty(o)) {
log.debug("key:{}", list.get(i));
String value = o.toString();
if (!isChineseChar(value))
sb.append(value);
}
}
}
log.info("-----------usign text:{}-------------", sb);
if (MD5.md5(sb.toString(), key).equals(reqMap.get(SIGN)))
return true;
} catch (Exception e) {
log.error(e.getMessage(),e);
}
return false;
}
public static boolean isChineseChar (String text){
boolean temp = false;
Pattern p = Pattern.compile("[\u4e00-\u9fa5]");
Matcher m = p.matcher(text);
if (m.find()) {
temp = true;
}
return temp;
}
如传入的
{
"username":"admin",
"password":"test",
...
}
对username password 对key进行字典排序,再加上某个约定的值,进行md5签名。 封装成"sign":"....."传入后台
后台对所有数据进行同样的签名,生成的签名字符串 与前端传入的sign值 进行比对。 防止对业务数据进行篡改。
此处的逻辑也可以进行相关的修改,可以对keyvalue&keyvalue&keyvalue&约定的值 具体看业务场景,前后端保持一致即可。