隐藏

C#微信退费

发布:2023/5/31 11:21:31作者:管理员 来源:本站 浏览次数:362



C#微信退费全过程


//调用退费

public void WeChatRefund(string total_fee,string refund_fee,string transaction_id){

  string totalfee= (float.Parse(total_fee) * 100).ToString();//订单总价

               string refundfee= (float.Parse(refund_fee) * 100).ToString();//退费金额

               string res = RefundRun(transaction_id, "", totalfee, refundfee);//调用退费方法

               if (res.Contains("return_msg=OK")){

               //退费成功

               }

               else{

               //退费失败

               }

  }

    /***

  * 申请退款完整业务流程逻辑

    * @param transaction_id 微信订单号(优先使用)

    * @param out_trade_no 商户订单号

    * @param total_fee 订单总金额

    * @param refund_fee 退款金额

    * @return 退款结果(xml格式)

    */

    public static string RefundRun(string transaction_id, string out_trade_no, string total_fee, string refund_fee)

    {

        Log.Info("Refund", "Refund is processing...");


        WxPayData data = new WxPayData();

        if (!string.IsNullOrEmpty(transaction_id))//微信订单号存在的条件下,则已微信订单号为准

        {

            data.SetValue("transaction_id", transaction_id);

        }

        else//微信订单号不存在,才根据商户订单号去退款

        {

            data.SetValue("out_trade_no", out_trade_no);

        }


        data.SetValue("total_fee", int.Parse(total_fee));//订单总金额

        data.SetValue("refund_fee", int.Parse(refund_fee));//退款金额

        data.SetValue("out_refund_no", WxPayApi.GenerateOutTradeNo());//随机生成商户退款单号

        data.SetValue("op_user_id", MchID);//操作员,默认为商户号


        WxPayData result = Refund(data);//提交退款申请给API,接收返回数据


        Log.Info("Refund", "Refund process complete, result : " + result.ToXml());

        return result.ToPrintStr();

    }

 /**

       *

       * 申请退款

       * @param WxPayData inputObj 提交给申请退款API的参数

       * @param int timeOut 超时时间

       * @throws WxPayException

       * @return 成功时返回接口调用结果,其他抛异常

       */

       public static WxPayData Refund(WxPayData inputObj, int timeOut = 6)

       {

           string url = "https://api.mch.weixin.qq.com/secapi/pay/refund";

           //检测必填参数

           if (!inputObj.IsSet("out_trade_no") && !inputObj.IsSet("transaction_id"))

           {

               throw new WxPayException("退款申请接口中,out_trade_no、transaction_id至少填一个!");

           }

           else if (!inputObj.IsSet("out_refund_no"))

           {

               throw new WxPayException("退款申请接口中,缺少必填参数out_refund_no!");

           }

           else if (!inputObj.IsSet("total_fee"))

           {

               throw new WxPayException("退款申请接口中,缺少必填参数total_fee!");

           }

           else if (!inputObj.IsSet("refund_fee"))

           {

               throw new WxPayException("退款申请接口中,缺少必填参数refund_fee!");

           }

           else if (!inputObj.IsSet("op_user_id"))

           {

               throw new WxPayException("退款申请接口中,缺少必填参数op_user_id!");

           }


           inputObj.SetValue("appid",AppID);//公众账号ID

           inputObj.SetValue("mch_id", MchID);//商户号

           inputObj.SetValue("nonce_str", Guid.NewGuid().ToString().Replace("-", ""));//随机字符串

           inputObj.SetValue("sign_type", WxPayData.SIGN_TYPE_MD5);//签名类型

           inputObj.SetValue("sign", inputObj.MakeSign());//签名

           

           string xml = inputObj.ToXml();

           var start = DateTime.Now;


           Log.Debug("WxPayApi", "Refund request : " + xml);

           string response = HttpServiceWeChat.Post(xml, url, true, timeOut);//调用HTTP通信接口提交数据到API

           Log.Debug("WxPayApi", "Refund response : " + response);


           var end = DateTime.Now;

           int timeCost = (int)((end - start).TotalMilliseconds);//获得接口耗时


           //将xml格式的结果转换为对象以返回

           WxPayData result = new WxPayData();

           result.FromXml(response);


           ReportCostTime(url, timeCost, result);//测速上报


           return result;

       }

        public static string Post(string xml, string url, bool isUseCert, int timeout)

       {

           System.GC.Collect();//垃圾回收,回收没有正常关闭的http连接


           string result = "";//返回结果


           HttpWebRequest request = null;

           HttpWebResponse response = null;

           Stream reqStream = null;


           try

           {

               //设置最大连接数

               ServicePointManager.DefaultConnectionLimit = 200;

               //设置https验证方式

               if (url.StartsWith("https", StringComparison.OrdinalIgnoreCase))

               {

                   ServicePointManager.ServerCertificateValidationCallback =

                           new RemoteCertificateValidationCallback(CheckValidationResult);

               }


               /***************************************************************

               * 下面设置HttpWebRequest的相关属性

               * ************************************************************/

               request = (HttpWebRequest)WebRequest.Create(url);

               request.UserAgent = USER_AGENT;

               request.Method = "POST";

               request.Timeout = timeout * 1000;


               //设置POST的数据类型和长度

               request.ContentType = "text/xml";

               byte[] data = System.Text.Encoding.UTF8.GetBytes(xml);

               request.ContentLength = data.Length;


               //是否使用证书

               if (isUseCert)

               {

                   X509Certificate2 cert = new X509Certificate2(证书路径,密码);

                   request.ClientCertificates.Add(cert);

                   Log.Debug("WxPayApi", "PostXml used cert");

               }


               //往服务器写入数据

               reqStream = request.GetRequestStream();

               reqStream.Write(data, 0, data.Length);

               reqStream.Close();


               //获取服务端返回

               response = (HttpWebResponse)request.GetResponse();


               //获取服务端返回数据

               StreamReader sr = new StreamReader(response.GetResponseStream(), Encoding.UTF8);

               result = sr.ReadToEnd().Trim();

               sr.Close();

           }

           catch (System.Threading.ThreadAbortException e)

           {

               Log.Error("HttpService", "Thread - caught ThreadAbortException - resetting.");

               Log.Error("Exception message: {0}", e.Message);

               System.Threading.Thread.ResetAbort();

           }

           catch (WebException e)

           {

               Log.Error("HttpService", e.ToString());

               if (e.Status == WebExceptionStatus.ProtocolError)

               {

                   Log.Error("HttpService", "StatusCode : " + ((HttpWebResponse)e.Response).StatusCode);

                   Log.Error("HttpService", "StatusDescription : " + ((HttpWebResponse)e.Response).StatusDescription);

               }

               throw new WxPayException(e.ToString());

           }

           catch (Exception e)

           {

               Log.Error("HttpService", e.ToString());

               throw new WxPayException(e.ToString());

           }

           finally

           {

               //关闭连接和流

               if (response != null)

               {

                   response.Close();

               }

               if(request != null)

               {

                   request.Abort();

               }

           }

           return result;

       }


  


大体的退费代码就是这些,具体没有体现,接下来是退费发布时遇到的问题

1.“路径正确,一直报系统找不到路径问题”

找到对应应用程序池,将其"高级设置"–“进程模型”–“加载用户配置文件” 设置为true


2.“IIS证书发布问题”

首先将下载的证书导入到服务器或本地。点击证书

win+R 输入MMC,打开MMC


添加证书

完成即可。