【移动支付】.NET微信扫码支付接入(模式二-NATIVE)

时间:2022-12-12 15:45:44

一、前言

      经过两三天的琢磨总算完成了微信扫码支付功能,不得不感叹几句:

  1. 微信提供的DEMO不错,直接复制粘贴就可以跑起来了;
  2. 微信的配置平台我真是服了。公众平台、商户平台、开放平台,一个平台一套账户密码,大写的恶心

DEMO地址:https://pay.weixin.qq.com/wiki/doc/api/native.php?chapter=11_1

.NET版DEMO中的Lib文件夹是关键,直接复制到自己的代码里,或者打成dll随个人意愿。

二、正文

      Step1:肯定是产生商户订单号,然后传给微信后台,由微信去组成二维码字符串,然后返给你,你再把字符串做成图片;

        /// <summary>
/// 获取二维码
/// </summary>
/// <param name="orderNumber"></param>
/// <returns></returns>
public string GetCodeUrl(string orderNumber)
{
var result = string.Empty;
if (!string.IsNullOrEmpty(orderNumber))
{
var matchedItem = db.OrderInfoForProducts.FirstOrDefault(x => x.OrderNumber == orderNumber);
if (matchedItem != null && matchedItem.IsPaid == false)
{
WxPayData data = new WxPayData();
data.SetValue("body", "productBody");//商品描述
data.SetValue("attach", "attach data");//附加数据
data.SetValue("out_trade_no", WxPayApi.GenerateOutTradeNo());//随机字符串
data.SetValue("total_fee", price);//总金额
data.SetValue("time_start", DateTime.Now.ToString("yyyyMMddHHmmss"));//交易起始时间
data.SetValue("time_expire", DateTime.Now.AddMinutes().ToString("yyyyMMddHHmmss"));//交易结束时间
data.SetValue("goods_tag", "tag");//商品标记
data.SetValue("trade_type", "NATIVE");//交易类型
data.SetValue("product_id", WxPayApi.GenerateOutTradeNo());//商品ID
result = WxPayApi.UnifiedOrder(data).GetValue("code_url").ToString();//调用统一下单接口
}
}
return result;
}

在这里,我是把公司的商户订单号放在了attach字段上,因为公司的商户订单号比较长,超过了32位。out_trade_no与product_id字段最多32位,请慎重!微信中的价格不能带小数,所以0.01元要写成100

Step2: 成功返回二维码字符串之后就可以在生成图片了,我这边使用了ThoughtWorks.QRCode.dll来生成图片:

        /// <summary>
/// 根据字符串得到相应的二维码
/// </summary>
/// <param name="qrInfo"></param>
/// <param name="productName"></param>
/// <param name="version"></param>
/// <returns></returns>
public static Image CreateQRCodeImage(string qrInfo, string productName, string version)
{
try
{
if (!string.IsNullOrEmpty(qrInfo))
{
QRCodeEncoder encoder = new QRCodeEncoder
{
QRCodeEncodeMode = QRCodeEncoder.ENCODE_MODE.BYTE,
QRCodeScale = ,
QRCodeVersion = ,
QRCodeErrorCorrect = QRCodeEncoder.ERROR_CORRECTION.M
};
//编码方式(注意:BYTE能支持中文,ALPHA_NUMERIC扫描出来的都是数字)
//大小(值越大生成的二维码图片像素越高)
//版本(注意:设置为0主要是防止编码的字符串太长时发生错误)
//错误效验、错误更正(有4个等级) Image image = encoder.Encode(qrInfo, Encoding.GetEncoding("utf-8"));
string filename = $"{productName}_{version}.png";
var userLocalPath = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData);
var docPath = Path.Combine(userLocalPath, @"Your Product\QRCode");
if (!Directory.Exists(docPath))
{
Directory.CreateDirectory(docPath);
}
string filepath = Path.Combine(docPath, filename);
using (FileStream fs = new FileStream(filepath, FileMode.OpenOrCreate, FileAccess.Write))
{
image.Save(fs, System.Drawing.Imaging.ImageFormat.Png);
fs.Close();
image.Dispose();
}
return image;
}
}
catch (Exception)
{
return null;
}
return null;
}

         Step3: 当用户扫完二维码之后,微信会发起回调,这时候我们就可以处理自己的业务逻辑了。这里我的UpdatePayStatus返回的是一个空页面

        /// <summary>
/// 回调函数
/// </summary>
public ActionResult UpdatePayStatus()
{
//接收从微信后台POST过来的数据
System.IO.Stream s = Request.InputStream;
int count = ;
byte[] buffer = new byte[];
StringBuilder builder = new StringBuilder();
while ((count = s.Read(buffer, , )) > )
{
builder.Append(Encoding.UTF8.GetString(buffer, , count));
}
s.Flush();
s.Close();
s.Dispose(); //转换数据格式并验证签名
WxPayData data = new WxPayData();
try
{
data.FromXml(builder.ToString());
}
catch (WxPayException ex)
{
//若签名错误,则立即返回结果给微信支付后台
WxPayData res = new WxPayData();
res.SetValue("return_code", "FAIL");
res.SetValue("return_msg", ex.Message); LogEntity signErrorLog = new LogEntity();
signErrorLog.errorMessage = ex.Message;
LogHelper.WriteLog(signErrorLog, null); Response.Write(res.ToXml());
Response.End();
} ProcessNotify(data);
return View();
} /// <summary>
/// 处理回调数据
/// </summary>
/// <param name="data"></param>
public void ProcessNotify(WxPayData data)
{
WxPayData notifyData = data;
//检查支付结果中transaction_id是否存在
if (!notifyData.IsSet("transaction_id"))
{
//若transaction_id不存在,则立即返回结果给微信支付后台
WxPayData res = new WxPayData();
res.SetValue("return_code", "FAIL");
res.SetValue("return_msg", "支付结果中微信订单号不存在"); LogEntity orderLog = new LogEntity();
orderLog.errorMessage = "支付结果中微信订单号不存在";
LogHelper.WriteLog(orderLog, null); Response.Write(res.ToXml());
Response.End();
} string transaction_id = notifyData.GetValue("transaction_id").ToString(); //查询订单,判断订单真实性
if (!QueryOrder(transaction_id))
{
//若订单查询失败,则立即返回结果给微信支付后台
WxPayData res = new WxPayData();
res.SetValue("return_code", "FAIL");
res.SetValue("return_msg", "订单查询失败"); LogEntity orderqueryLog = new LogEntity();
orderqueryLog.errorMessage = "订单查询失败";
LogHelper.WriteLog(orderqueryLog, null); Response.Write(res.ToXml());
Response.End();
}
//查询订单成功
else
{
WxPayData res = new WxPayData();
res.SetValue("return_code", "SUCCESS");
res.SetValue("return_msg", "OK"); SetPaymentResult(data); //这里的参数是 data !!! 不是 res !!! Response.Write(res.ToXml());
Response.End();
}
} /// <summary>
/// 商户后台更新
/// </summary>
/// <param name="res"></param>
private void SetPaymentResult(WxPayData res)
{
var isSucessFlagOne = res.GetValue("return_code").ToString();
var isSuccessFlagTwo = res.GetValue("result_code").ToString(); if (isSucessFlagOne == "SUCCESS" && isSuccessFlagTwo == "SUCCESS")
{
//自己的业务逻辑 !!!!
}
} //查询订单
private bool QueryOrder(string transaction_id)
{
WxPayData req = new WxPayData();
req.SetValue("transaction_id", transaction_id);
WxPayData res = WxPayApi.OrderQuery(req);
if (res.GetValue("return_code").ToString() == "SUCCESS" &&
res.GetValue("result_code").ToString() == "SUCCESS")
{
return true;
}
else
{
return false;
}
}

三、结尾

      做完支付宝与微信扫码支付发现支付宝的接入要比微信方便很多,还有一个同步请求。而且吐槽个其它的,微信开放平台的审批速度要比支付宝的审批慢很多。还有微信支付最后上线前不需要非得用沙箱测试,做完之后直接一分钱一分钱测试即可。

【移动支付】.NET微信扫码支付接入(模式二-NATIVE)的更多相关文章

  1. thinkphp&period;2 thinkphp5微信支付 微信公众号支付 thinkphp 微信扫码支付 thinkphp 微信企业付款5

    前面已经跑通了微信支付的流程,接下来吧微信支付和微信企业付款接入到thinkphp中,版本是3.2 把微信支付类.企业付款类整合到一起放到第三方类库,这里我把微信支付帮助类和企业付款类放到同一个文件了 ...

  2. 微信支付-微信公众号支付,微信H5支付,微信APP支付,微信扫码支付

    在支付前,如果使用第三方MVC框架,则使用重写模式,服务器也需要配置该项 if (!-e $request_filename){ rewrite ^/(.*)$ /index.php/$ last; ...

  3. 微信公众号支付&vert;微信H5支付&vert;微信扫码支付&vert;小程序支付&vert;APP微信支付解决方案总结

    最近负责的一些项目开发,都用到了微信支付(微信公众号支付.微信H5支付.微信扫码支付.APP微信支付).在开发的过程中,在调试支付的过程中,或多或少都遇到了一些问题,今天总结下,分享,留存. 先说注意 ...

  4. C&num;版微信公众号支付&vert;微信H5支付&vert;微信扫码支付问题汇总及解决方案总结

    最近负责的一些项目开发,都用到了微信支付(微信公众号支付.微信H5支付.微信扫码支付).在开发的过程中,在调试支付的过程中,或多或少都遇到了一些问题,今天总结下,分享,留存.代码在文章结尾处,有需要的 ...

  5. ASP&period;NET Core Web 支付功能接入 微信-扫码支付篇

    这篇文章将介绍ASP.NET Core中使用 开源项目 Payment,实现接入微信-扫码支付及异步通知功能. 开发环境:Win 10 x64.VS2017 15.6.4..NET Core SDK ...

  6. 【转载】ASP&period;NET Core Web 支付功能接入 微信-扫码支付篇

    转自:http://www.cnblogs.com/essenroc/p/8630730.html 这篇文章将介绍ASP.NET Core中使用 开源项目 Payment,实现接入微信-扫码支付及异步 ...

  7. ASP&period;NET Core Web 支付功能接入 微信-扫码支付篇(转)

    原文 https://www.cnblogs.com/essenroc/p/8630730.html // 随着版本更迭,新版本可能无法完全适用,请参考仓库内的示例. 这篇文章将介绍ASP.NET C ...

  8. 微信扫码支付PHP接入总结

    微信扫码支付分为两种模式, 模式一比较复杂,需要公众号配置回调地址. 模式二比较简单,只需要在代码中配置回调地址就可以了. 我这次使用的是模式二. 需要配置参数, const APPID = 'xxx ...

  9. PHP PC端微信扫码支付【模式二】详细教程-附带源码(转)

    博主写这破玩意儿的时候花了大概快两天时间才整体的弄懂逻辑,考虑了一下~还是把所有代码都放出来给大家~抱着开源大无私的精神!谁叫我擅长拍黄片呢?同时也感谢我刚入行时候那些无私帮过我的程序员们! 首先还是 ...

随机推荐

  1. 知名黑客组织Anonymous(匿名者)的装备库

    原文出处: infosecinstitute   译文出处:freebuf   欢迎分享原创到伯乐头条 本文关注的是世界著名的黑客组织Anonymous(匿名者).“我将描述他们的攻击方法和方式的计划 ...

  2. 解决:对 PInvoke 函数的调用导致堆栈不对称问题

    解决:对 PInvoke 函数的调用导致堆栈不对称问题 问题描述: 在使用托管代码调用非托管代码时,发生“对 PInvoke 函数“UseTwiHikVisionDllTest!UseTwiHikVi ...

  3. 智联卓聘 卓聘IM&lpar;聊聊&rpar;开发实践

    1.  卓聘IM开发背景 智联卓聘是智联旗下高端人才招聘平台,成立快4年多,业务增涨每年以100%速度增涨快,同时对产品和研发速度都比较高. 2015年提出IM开发,主要用于后选人与猎头及时交流,降低 ...

  4. &period;Net &num;if DEBUG调试模式代码使用

    #if DEBUG      Console.WriteLine("DEBUG:11111111111"); #else       Console.WriteLine(&quot ...

  5. js事件冒泡和事件捕捉

    结论:他们是描述事件触发时序问题的术语.事件捕获指的是从document到触发事件的那个节点,即自上而下的去触发事件.相反的,事件冒泡是自下而上的去触发事件.绑定事件方法的第三个参数,就是控制事件触发 ...

  6. JavaFX

    [AWT-SWING-JAVA FX] 多平台.多应用的现有通用类 [inner class] (member class)inside another class, outside any meth ...

  7. 在VS中安装&sol;使用 MVVMLight

    一般来说,我喜欢使用NuGet来获取这些东西,比如Newtonsoft.Json.netlog4.MVVMLight 之类的东西.至于NuGet的使用,以后再说吧.为了直接进入正题,我们这里直接使用V ...

  8. TINY4412:移植uboot、内核和挂接网络文件系统

    开发环境: 单板:TINY4412-1611 系统:Ubuntu 16.04 64位 编译工具链:arm-linux-gcc-4.3.2 uboot版本:uboot_tiny4412-20130729 ...

  9. bzoj1211&colon; &lbrack;HNOI2004&rsqb;树的计数(purfer编码)

    BZOJ1005的弱化版,不想写高精度就可以写这题嘿嘿嘿 purfer编码如何生成?每次将字典序最小的叶子节点删去并将其相连的点加入序列中,直到树上剩下两个节点,所以一棵有n个节点的树purfer编码 ...

  10. 清理widows的网络连接

    在听兄弟连李明老师的课程时,Samba配置时,window连接有时要清理,可以用以下命令 1.打开win的命令行. 2.输入net use,就会打印出当前缓存的连接上列表. 3.根据列表,一个个删除连 ...