每一个值从a到z的顺序排序,若遇到相同首字母,则看第二个字母,以此类推

3.4安全码

计算安全码使用的算法 SHA1

3.4.1安全码原文

将所有“名值对”和APIKey拼接

名值对 APIKey
key1=value1&key2=value2…每一个值从a到z的顺序排序,若遇到相同首字母,则看第二个字母,以此类推 AppId对应的APIKey值,Base64值

比如名值对字母升序之后 a=value1&b=value2&c=value3;APIKey是QVBJS2V5,安全码原文=
a=value1&b=value2&c=value3QVBJS2V5

3.4.2注意

  1. 计算之前需要将原文以UTF-8字符集编码为字节数组;
  2. 根据HTTP协议要求,传递参数的值中如果含有特殊字符(如@、+、/),该值需要做URL Encoding,这样服务中心才能接收到正确的参数值;
  3. 不管是否含有特殊字符,安全码原文使用原始值。

3.4.3请求参数安全码原文格式

安全码原文包含(1)业务参数、(2)除安全码之外平台接入参数、(3)APIKey三部分。比如 “根据票据代码、票号、随机码”接口的安全码原文:

举例
appId=XXX&dataType=XXX&eInvoiceCode=XXX&eInvoiceNumber=XXX&randomNumber=XXX&serviceName=XXXYYY

dataType=XXX&eInvoiceCode=XXX&eInvoiceNumber=XXX&randomNumber=XXX表示业务参数
appIdserviceName表示平台参数
YYY表示APIKey,原文末尾

3.4.4返回值安全码原文格式

安全码原文中包含statusmessagedata、APIKey四部分

  1. 比如 “根据票据代码、票号、随机码”接口失败时安全码原文:
    APIKey=XXX&message=message原文&status=status原文
  2. 比如 “根据票据代码、票号、随机码”接口成功时安全码原文:
    APIKey=XXX[&data=data原文]&message=message原文&status=status原文

代码参考

  • 拼接
public static void main(String[] args) throws Exception {
        Map<String, String>params = new HashMap<>();
        params.put("appId", "XXX");
        params.put("serviceName", "checkAccount");
        params.put("dataType", "json");
        String builderSignStr = builderSignStr(params);
        String apiKey = "APIKey";
        byte[] securityCode= EncryptUtils.hmac(apiKey, builderSignStr + apiKey);
        // 转化securityCode 为 base64 字符串
        System.out.println(securityCode);
    }

    public static String builderSignStr(Map<String, String> params) {
        Set<String> keySet = params.keySet();
        List<String>keyList = new ArrayList<String>(keySet);
        Collections.sort(keyList);
        StringBuilder sb = new StringBuilder();
        for (String key : keyList) {
            sb.append(key);
            sb.append("=");
            sb.append(params.get(key));
            sb.append("&");
        }
        sb.deleteCharAt(sb.length() - 1);
        return sb.toString();
    }
    public static String md5(String plaintext) {
        assert plaintext != null : "plaintext may arg not be null";
        byte[] bytes = null;
        String encoded = "";
        try {
            MessageDigest digest = MessageDigest.getInstance("MD5");
            digest.reset();
            digest.update(plaintext.getBytes(Charset.forName("utf-8")));
            bytes = digest.digest();
            encoded = Base64.encodeBytes(bytes);
        } catch (NoSuchAlgorithmException e) {
            //throw new EncryptException(e.getMessage(), e);
        }
        return encoded;
    }
  • 每一个值从a到z的顺序排序,若遇到相同首字母,则看第二个字母,以此类推
    public static void main(String[] args) throws Exception {
        java.util.SortedMap<String, String> packageParams = new TreeMap<String, String>();
        packageParams.put("status", "{merBillNo:2015090700000000}");
        packageParams.put("message", "2015090700000000");
        packageParams.put("data", "2015090700000000");
        String str = new SortedMap().createSign(packageParams);
        System.out.println(str);

        String str2 = new SortedMap().createSign2(packageParams);
        System.out.println(str2);
    }
    /**
     * 规则是:按参数名称a-z排序,遇到空值的参数不参加签名。V型知识库www.vxzsk.com
     */
    public String createSign(java.util.SortedMap<String, String> packageParams) throws Exception {
        StringBuffer sb = new StringBuffer();
        Set<?> es = packageParams.entrySet();
        Iterator<?> it = es.iterator();
        while (it.hasNext()) {
            Map.Entry entry = (Map.Entry) it.next();
            String k = (String) entry.getKey();
            String v = (String) entry.getValue();
            if (null != v && !"".equals(v) && !"sign".equals(k) && !"key".equals(k)) {
                sb.append(k + "=" + v + "&");
            }
        }
        sb.append("key=XXXXXXXXXXXXXXXXXXXXXXXXXXXXXX");
        return sb.toString();
    }
    /**
     * 规则是:按参数名称a-z排序,遇到空值的参数不参加签名。V型知识库www.vxzsk.com
     */
    public String createSign2(java.util.SortedMap<String, String> packageParams) throws Exception {
        StringBuffer sb = new StringBuffer();
        if (packageParams != null) {
            for (Map.Entry entry : packageParams.entrySet()) {
                String k = (String) entry.getKey();
                String v = (String) entry.getValue();
                if (null != v && !"".equals(v) && !"sign".equals(k) && !"key".equals(k)) {
                    sb.append(k + "=" + v + "&");
                }
            }
        }
        sb.append("key=XXXXXXXXXXXXXXXXXXXXXXXXXXXXXX");
        return sb.toString();
    }

发布了83 篇原创文章 · 获赞 24 · 访问量 7万+

猜你喜欢

转载自blog.csdn.net/u010638673/article/details/90373263
今日推荐