前言:api裸奔时代已结束,企业级高可用api设防腾讯sign设计与实现。。。
设计起来就是头冷。。。
有三个关键点:接口参数加密+时效性验证+私钥
首先定义几个参数:
int age = 0;
String app_id = "123";
String name = "撒旦法";
String nonce_str = _stringUtil.getCharAndNumr(16, 3);
String sign = "";
String time_stamp = _timeUtil.getTimeStamp();
String app_key = "123456";
就是一个姓名为XX年龄为Y的appid用户在time_stamp这个时间拿着app_key钥匙nonce_str 随机打开sign 门,然后偷窃。。。
偷窃未遂,这很安全吧。。。
首先要确定偷哪个房屋,sign门需求确定。
sign = YhSignSort.getSignature(map);
// System.out.println("生成的sign参数:" + sign);
怎么确定?偷了穷的人家怎么办,我们是劫富济贫的,所以需要调研。。。
算法实现
签名算法采用MD5摘要方式实现,步骤如下:
1、将参数对按key进行字典升序排序,得到有序的参数对列表N
2、将列表N中的参数对按URL键值对的格式拼接成字符串,得到字符串T(如:key1=val1&key2=val2),值使用URL编码
3、将应用密钥以app_key为键名,组成URL键值拼接到字符串T末尾,得到字符串S(如:key1=val1&key2=val2&app_key=密钥)
4、对字符串S进行MD5摘要计算,将得到的md5值转换成大写,最终得到接口请求签名
String secret = "123456"; //把secret加入进行加密 MD5盐值加密app_id 这里很多加密算法 现在假设加密结果是123456
boolean a = validateTimeStamp(time_stamp);
if (a) {
System.out.println("time_stamp参数无效"); //请检查time_stamp距离当前时间是否超过5分钟
}
// map.put("nonce_str", "");
// map.put("age", "");
// map.put("app_id", "123");
if("".equals(map.get("app_id"))){
System.out.println("缺少app_id参数");
}else if(!"123".equals(map.get("app_id"))){
System.out.println("appid应用不存在");
}else if("".equals(map.get("time_stamp"))){
System.out.println("缺少time_stamp参数");
}else if("".equals(map.get("nonce_str"))){
System.out.println("缺少nonce_str参数");
}else if(validateSign(map,sign)){
if("123456".equals(secret)){
System.out.println("验证成功");
}else{
System.out.println("缺失API权限");
}
}else{
System.out.println("请求签名无效");
}
validateTimeStamp方法是验证失效性
validateSign方法是验证签名正确性
一个app_id对应多个应用,只要app_key正确,可以访问,否则访问失败。app_key是根据app_id
加密加密生成,可以怎么生成也行,只要不被破解,或告诉别人,也可以重新生成。
需要源代码学习,可加QQ490647751回复‘开通vip——App开放接口api安全性—防腾讯签名sign的设计与实现’获取。