随着json的盛行,很多接口签名都会用到json形势的body体。而在对json进行签名和对方验签的时候,在组装json字符串时候,json中key排序的规则、顺序,会直接影响签名结果。所以,一个完善的接口说明,如果json内容参与签名,是务必要规范json排序规则的。
以下实现了,根据json中的key,按照ascii升序排序。
JSONObject json = new JSONObject();//默认无序
json.put("account", "111111");
json.put("domain", "11111");
json.put("status",1);
json.put("passwd", DigestUtils.md5DigestAsHex("test".getBytes()));
json.put("tag", System.currentTimeMillis());
json.put("ts", System.currentTimeMillis());
json.put("gid", "67");
json.put("xe", new String(Base64Utils.encode("测试".getBytes("GBK"))));
默认输出:
{“gid”:“67”,“passwd”:“098f6bcd4621d373cade4e832627b4f6”,“domain”:“11111”,“tag”:1684370379044,“xe”:“suLK1A==”,“account”:“111111”,“status”:1,“ts”:1684370379044}
可以看到,key的顺序并不符合预期。
通过如下代码排序
SortedMap<String,Object> sMap = new TreeMap<>(json);
JSONObject sortJson = new JSONObject(true);//表示有序的json,不参与排序,
sortJson.putAll(sMap);
System.out.println(sortJson.toString());
输出结果:
{“account”:“111111”,“domain”:“11111”,“gid”:“67”,“passwd”:“098f6bcd4621d373cade4e832627b4f6”,“status”:1,“tag”:1684370960447,“ts”:1684370960447,“xe”:“suLK1A==”}
以上实现了json根据key升序排序。
当需要对JSONArray中的json进行排序,
JSONArray array = JSONArray.parseArray("[{'msg':'ccc','phoneNumbers':'139033333','signName':'APP'},{'msg':'b','phoneNumbers':'139011111','signName':'APP'},{'msg':'d','phoneNumbers':'139000000','signName':'APP'}]");
System.out.println(array);
输出结果如下,json中内容是无序的:
[{“msg”:“ccc”,“signName”:“APP”,“phoneNumbers”:“139033333”},{“msg”:“b”,“signName”:“APP”,“phoneNumbers”:“139011111”},{“msg”:“d”,“signName”:“APP”,“phoneNumbers”:“139000000”}]
JSONArray array2 = new JSONArray();
for(int i = 0; i < array.size(); i++) {
JSONObject tempJson = (JSONObject) array.get(i);
SortedMap<String,Object> sMap = new TreeMap<>(tempJson);
JSONObject sortJson = new JSONObject(true);//表示有序的json,不参与排序
sortJson.putAll(sMap);
array2.add(sortJson);
}
System.out.println(array2);
排序后输出内容:
[{“msg”:“ccc”,“phoneNumbers”:“139033333”,“signName”:“APP”},{“msg”:“b”,“phoneNumbers”:“139011111”,“signName”:“APP”},{“msg”:“d”,“phoneNumbers”:“139000000”,“signName”:“APP”}]