zoukankan      html  css  js  c++  java
  • 微信支付.NET SDK 中的BUG(存疑)

    BUG出现在类文件WxPayData.cs中的FromXml(string xml)方法

     1  /**
     2         * @将xml转为WxPayData对象并返回对象内部的数据
     3         * @param string 待转换的xml串
     4         * @return 经转换得到的Dictionary
     5         * @throws WxPayException
     6         */
     7         public SortedDictionary<string, object> FromXml(string xml)
     8         {
     9             if (string.IsNullOrEmpty(xml))
    10             {
    11                 Log.Error(this.GetType().ToString(), "将空的xml串转换为WxPayData不合法!");
    12                 throw new WxPayException("将空的xml串转换为WxPayData不合法!");
    13             }
    14 
    15             
    16             SafeXmlDocument xmlDoc = new SafeXmlDocument();
    17             xmlDoc.LoadXml(xml);
    18             XmlNode xmlNode = xmlDoc.FirstChild;//获取到根节点<xml>
    19             XmlNodeList nodes = xmlNode.ChildNodes;
    20             foreach (XmlNode xn in nodes)
    21             {
    22                 XmlElement xe = (XmlElement)xn;
    23                 m_values[xe.Name] = xe.InnerText;//获取xml的键值对到WxPayData内部的数据中
    24             }
    25             
    26             try
    27             {
    28                 //2015-06-29 错误是没有签名
    29                 if(m_values["return_code"] != "SUCCESS")
    30                 {
    31                     return m_values;
    32                 }
    33                 CheckSign();//验证签名,不通过会抛异常
    34             }
    35             catch(WxPayException ex)
    36             {
    37                 throw new WxPayException(ex.Message);
    38             }
    39 
    40             return m_values;
    41         }

    根据VS代码提示 ,可能非有意的引用比较;左侧需要强制转换。

    经调试监听,即使m_values["return_code"]返回值为SUCCESS,此处判断也是true。这样就绕过了CheckSign()验证签名的方法。

    如果按照VS代码提示进行修改:

        //2015-06-29 错误是没有签名
                    if(m_values["return_code"].ToString() != "SUCCESS")
                    {
                        return m_values;
                    }
                    CheckSign();//验证签名,不通过会抛异常

    经调试,m_values["return_code"]返回值为SUCCESS,下一步走CheckSign()验证签名的方法,然后报“WxPayData字段数据类型错误!”

    然后下载Java SDK进行代码对比,发现只要m_values["return_code"]返回值为SUCCESS,就要进行签名验证,Java代码如下

    /**
         * 处理 HTTPS API返回数据,转换成Map对象。return_code为SUCCESS时,验证签名。
         * @param xmlStr API返回的XML格式数据
         * @return Map类型数据
         * @throws Exception
         */
        public Map<String, String> processResponseXml(String xmlStr) throws Exception {
            String RETURN_CODE = "return_code";
            String return_code;
            Map<String, String> respData = WXPayUtil.xmlToMap(xmlStr);
            if (respData.containsKey(RETURN_CODE)) {
                return_code = respData.get(RETURN_CODE);
            }
            else {
                throw new Exception(String.format("No `return_code` in XML: %s", xmlStr));
            }
    
            if (return_code.equals(WXPayConstants.FAIL)) {
                return respData;
            }
            else if (return_code.equals(WXPayConstants.SUCCESS)) {
               if (this.isResponseSignatureValid(respData)) {
                   return respData;
               }
               else {
                   throw new Exception(String.format("Invalid sign value in XML: %s", xmlStr));
               }
            }
            else {
                throw new Exception(String.format("return_code value %s is invalid in XML: %s", return_code, xmlStr));
            }
        }

    对于.NET SDK 中这个处理,不太明白。还请大神指点迷津!

  • 相关阅读:
    SQL 函数:Aggregate、Scalar函数介绍
    SQL 用于各种数据库的数据类型:MySQL、SQLsever
    SQL 通用数据类型解析
    SQL NULL 函数:使用方法及案例剖析
    SpringBoot的配置文件
    SpringBoot简介及快速入门
    本地仓库和远程仓库分支回退到指定的历史版本(idea)
    maven配置阿里云镜像仓库
    SSM三大框架整合-分模块版本
    Java程序调用Oracle存储过程和存储函数
  • 原文地址:https://www.cnblogs.com/dikeko/p/13496123.html
Copyright © 2011-2022 走看看