微信扫码支付有两种模式,

模式一和模式二,

两者具体的区别可参考官网文档:https://pay.weixin.qq.com/wiki/doc/api/native.php?chapter=6_4

微信官方的文档,这个扫码支付(NativePay)分为两种,一种是“生成扫描支付模式”,另外一种是“生成直接支付url,支付url有效期为2小时”,

具体适用什么场景请自行定义。

首先是申请微信支付,操作流程按照官方指引即可

申请成功后,官方会发送你一封关于商户平台信息的Email

接下来,我们就开始讲讲实际例子,

首先下载官方Demo,Demo地址:https://pay.weixin.qq.com/wiki/doc/api/native.php?chapter=11_1

环境准备工作:

然后将Demo的照搬到MVC工程中即可

然后就是配置lib文件夹里的Config文件,基本很多信息,在Email中都有包括

至于证书和商户支付密匙,则需要使用Emial的账户和密码去到微信商户平台去设置

配置完成后即可开始测试

如何生成:

模式一:

  1. string url1 = nativePay.GetPrePayUrl("",ref out_trade_no,UserId.ToString());
  2. ViewBag.TradeNo = out_trade_no;
  3. ViewBag.QRCode = "/WxMakeQRCode?data=" + HttpUtility.UrlEncode(url1);

模式二:

  1. string url2 = nativePay.GetPayUrl("123456", Money,ref out_trade_no,UserId.ToString());
  2. ViewBag.TradeNo = out_trade_no;
  3. ViewBag.QRCode = "/WxMakeQRCode?data=" + HttpUtility.UrlEncode(url2);
  1. public FileResult WxMakeQRCode(string data)
  2. {
  3. if (string.IsNullOrEmpty(data))
  4. throw new ArgumentException("data");
  5.  
  6. //初始化二维码生成工具
  7. QRCodeEncoder qrCodeEncoder = new QRCodeEncoder();
  8. qrCodeEncoder.QRCodeEncodeMode = QRCodeEncoder.ENCODE_MODE.BYTE;
  9. qrCodeEncoder.QRCodeErrorCorrect = QRCodeEncoder.ERROR_CORRECTION.M;
  10. qrCodeEncoder.QRCodeVersion = ;
  11. qrCodeEncoder.QRCodeScale = ;
  12.  
  13. //将字符串生成二维码图片
  14. Bitmap image = qrCodeEncoder.Encode(data, Encoding.Default);
  15.  
  16. //保存为PNG到内存流
  17. MemoryStream ms = new MemoryStream();
  18. image.Save(ms, ImageFormat.Jpeg);
  19.  
  20. return File(ms.ToArray(), "image/jpeg");
  21. }

 

主要注意的地方是,在第一种模式中,必须设定回调路径

模式二的回调路径是在Config中配置的

回调方法:

模式一:

  1. public class NativeNotifyController : Controller
  2. {
  3. // GET: NativeNotify
  4. public ActionResult Index()
  5. {
  6. string strData = ProcessNotify();
  7. Response.Write(strData);
  8. return View();
  9. }
  10.  
  11. public string ProcessNotify()
  12. {
  13. WxPayData notifyData = GetNotifyData();
  14.  
  15. //检查openid和product_id是否返回
  16. if (!notifyData.IsSet("openid") || !notifyData.IsSet("product_id"))
  17. {
  18. WxPayData res = new WxPayData();
  19. res.SetValue("return_code", "FAIL");
  20. res.SetValue("return_msg", "回调数据异常");
  21. return res.ToXml();
  22. }
  23.  
  24. //调统一下单接口,获得下单结果
  25. string openid = notifyData.GetValue("openid").ToString();
  26. string product_id = notifyData.GetValue("product_id").ToString();
  27. WxPayData unifiedOrderResult = new WxPayData();
  28. try
  29. {
  30. unifiedOrderResult = UnifiedOrder(openid, product_id);
  31. }
  32. catch (Exception ex)//若在调统一下单接口时抛异常,立即返回结果给微信支付后台
  33. {
  34. WxPayData res = new WxPayData();
  35. res.SetValue("return_code", "FAIL");
  36. res.SetValue("return_msg", "统一下单失败");
  37. return res.ToXml();
  38. }
  39.  
  40. //若下单失败,则立即返回结果给微信支付后台
  41. if (!unifiedOrderResult.IsSet("appid") || !unifiedOrderResult.IsSet("mch_id") || !unifiedOrderResult.IsSet("prepay_id"))
  42. {
  43. WxPayData res = new WxPayData();
  44. res.SetValue("return_code", "FAIL");
  45. res.SetValue("return_msg", "统一下单失败");
  46. return res.ToXml();
  47. }
  48.  
  49. //统一下单成功,则返回成功结果给微信支付后台
  50. WxPayData data = new WxPayData();
  51. data.SetValue("return_code", "SUCCESS");
  52. data.SetValue("return_msg", "OK");
  53. data.SetValue("appid", WxPayConfig.APPID);
  54. data.SetValue("mch_id", WxPayConfig.MCHID);
  55. data.SetValue("nonce_str", WxPayApi.GenerateNonceStr());
  56. data.SetValue("prepay_id", unifiedOrderResult.GetValue("prepay_id"));
  57. data.SetValue("result_code", "SUCCESS");
  58. data.SetValue("err_code_des", "OK");
  59. data.SetValue("sign", data.MakeSign());
  60. return data.ToXml();
  61. }
  62.  
  63. /// <summary>
  64. /// 接收从微信支付后台发送过来的数据并验证签名
  65. /// </summary>
  66. /// <returns>微信支付后台返回的数据</returns>
  67. public WxPayData GetNotifyData()
  68. {
  69. //接收从微信后台POST过来的数据
  70. System.IO.Stream s = Request.InputStream;
  71. int count = ;
  72. byte[] buffer = new byte[];
  73. StringBuilder builder = new StringBuilder();
  74. while ((count = s.Read(buffer, , )) > )
  75. {
  76. builder.Append(Encoding.UTF8.GetString(buffer, , count));
  77. }
  78. s.Flush();
  79. s.Close();
  80. s.Dispose();
  81.  
  82. //转换数据格式并验证签名
  83. WxPayData data = new WxPayData();
  84. try
  85. {
  86. data.FromXml(builder.ToString());
  87. }
  88. catch (WxPayException ex)
  89. {
  90. //若签名错误,则立即返回结果给微信支付后台
  91. WxPayData res = new WxPayData();
  92. res.SetValue("return_code", "FAIL");
  93. res.SetValue("return_msg", ex.Message);
  94. }
  95.  
  96. return data;
  97. }
  98.  
  99. private WxPayData UnifiedOrder(string openId, string productId)
  100. {
  101. //统一下单
  102. WxPayData req = new WxPayData();
  103. req.SetValue("body", "OBOT");
  104. req.SetValue("attach", "附加信息,用于后台或者存入数据库,做自己的判断");
  105. req.SetValue("out_trade_no", WxPayApi.GenerateOutTradeNo());
  106. req.SetValue("total_fee", );
  107. req.SetValue("time_start", DateTime.Now.ToString("yyyyMMddHHmmss"));
  108. req.SetValue("time_expire", DateTime.Now.AddMinutes().ToString("yyyyMMddHHmmss"));
  109. req.SetValue("goods_tag", "商品的备忘,可以自定义");
  110. req.SetValue("trade_type", "NATIVE");
  111. req.SetValue("openid", openId);
  112. req.SetValue("product_id", productId);
  113. WxPayData result = WxPayApi.UnifiedOrder(req);
  114. return result;
  115. }
  116. }

模式二:

  1. public class ResultNotifyController : Controller
  2. {
  3. // GET: ResultNotify
  4. public ActionResult Index()
  5. {
  6. string strData = ProcessNotify();
  7. Response.Write(strData);
  8. return View();
  9. }
  10.  
  11. public string ProcessNotify()
  12. {
  13. WxPayData notifyData = GetNotifyData();
  14.  
  15. //检查支付结果中transaction_id是否存在
  16. if (!notifyData.IsSet("transaction_id"))
  17. {
  18. //若transaction_id不存在,则立即返回结果给微信支付后台
  19. WxPayData res = new WxPayData();
  20. res.SetValue("return_code", "FAIL");
  21. res.SetValue("return_msg", "支付结果中微信订单号不存在");
  22. return res.ToXml();
  23. }
  24.  
  25. string transaction_id = notifyData.GetValue("transaction_id").ToString();
  26.  
  27. //查询订单,判断订单真实性
  28. if (!QueryOrder(transaction_id))
  29. {
  30. //若订单查询失败,则立即返回结果给微信支付后台
  31. WxPayData res = new WxPayData();
  32. res.SetValue("return_code", "FAIL");
  33. res.SetValue("return_msg", "订单查询失败");
  34. return res.ToXml();
  35. }
  36. //查询订单成功
  37. else
  38. {
  39. WxPayData res = new WxPayData();
  40. res.SetValue("return_code", "SUCCESS");
  41. res.SetValue("return_msg", "OK");
  42. Log.Info(this.GetType().ToString(), "order query success : " + res.ToXml());
  43. string strXml = res.ToXml();
  44. return res.ToXml();//如果我们走到这一步了,那就代表,用户已经支付成功了,所以,该干嘛干嘛了。
  45. }
  46. }
  47.  
  48. /// <summary>
  49. /// 接收从微信支付后台发送过来的数据并验证签名
  50. /// </summary>
  51. /// <returns>微信支付后台返回的数据</returns>
  52. public WxPayData GetNotifyData()
  53. {
  54. //接收从微信后台POST过来的数据
  55. System.IO.Stream s = Request.InputStream;
  56. int count = ;
  57. byte[] buffer = new byte[];
  58. StringBuilder builder = new StringBuilder();
  59. while ((count = s.Read(buffer, , )) > )
  60. {
  61. builder.Append(Encoding.UTF8.GetString(buffer, , count));
  62. }
  63. s.Flush();
  64. s.Close();
  65. s.Dispose();
  66.  
  67. Log.Info(this.GetType().ToString(), "Receive data from WeChat : " + builder.ToString());
  68.  
  69. //转换数据格式并验证签名
  70. WxPayData data = new WxPayData();
  71. try
  72. {
  73. data.FromXml(builder.ToString());
  74. }
  75. catch (WxPayException ex)
  76. {
  77. //若签名错误,则立即返回结果给微信支付后台
  78. WxPayData res = new WxPayData();
  79. res.SetValue("return_code", "FAIL");
  80. res.SetValue("return_msg", ex.Message);
  81. Log.Error(this.GetType().ToString(), "Sign check error : " + res.ToXml());
  82. return res;
  83. }
  84.  
  85. return data;
  86. }
  87.  
  88. //查询订单
  89. private bool QueryOrder(string transaction_id)
  90. {
  91. WxPayData req = new WxPayData();
  92. req.SetValue("transaction_id", transaction_id);
  93. WxPayData res = WxPayApi.OrderQuery(req);
  94. if (res.GetValue("return_code").ToString() == "SUCCESS" &&
  95. res.GetValue("result_code").ToString() == "SUCCESS")
  96. {
  97. return true;
  98. }
  99. else
  100. {
  101. return false;
  102. }
  103. }
  104. }

最终效果:

MVC 微信扫码支付的更多相关文章

  1. Net MVC微信扫码支付

    微信扫码支付+Asp.Net MVC 这里的扫码支付指的是PC网站上面使用微信支付,也就是官方的模式二,网站是Asp.net MVC,整理如下. 一.准备工作 使用的微信API中的统一下单方法,关键的 ...

  2. C# MVC微信扫码支付

    项目需求:学校学生网上缴费项目,刚来公司实习网上百度了各种资料,感谢很多大神避免了很多大坑. 本次扫码支付为:电脑生成二维码,手机微信扫码进行付款.建议开发前下载官方demo熟悉及后续有用到里面代码: ...

  3. .NET MVC结构框架下的微信扫码支付模式二 API接口开发测试

    直接上干货 ,我们的宗旨就是为人民服务.授人以鱼不如授人以渔.不吹毛求疵.不浮夸.不虚伪.不忽悠.一切都是为了社会共同进步,繁荣昌盛,小程序猿.大程序猿.老程序猿还是嫩程序猿,希望这个社会不要太急功近 ...

  4. ASP.NET Core Web 支付功能接入 微信-扫码支付篇

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

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

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

  6. asp.net core 微信扫码支付(扫码支付,H5支付,公众号支付,app支付)之1

    2018-08-13更新生成二维码的方法 在做微信支付前,首先要了解你需要什么方式的微信支付,目前本人做过的支付包含扫码支付.H5支付.公众号支付.App支付等,本人使用的是asp.net mvc c ...

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

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

  8. JAVA微信扫码支付模式二功能实现完整例子

    概述 本例子实现微信扫码支付模式二的支付功能,应用场景是,web网站微信扫码支付.实现从点击付费按钮.到弹出二维码.到用户用手机微信扫码支付.到手机上用户付费成功.web网页再自动调整到支付成功后的页 ...

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

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

随机推荐

  1. Flavors

    Flavors¶ Flavor interface. class novaclient.v1_1.flavors.Flavor(manager, info, loaded=False) Bases: ...

  2. 在网页中怎样给已发布的Flash添加链接的方法(zhuan)

    因为网页中的 Flash 是以控件形式出现的,优先级别较高,所以直接对它加链接是无效的,不过可以用按钮控件 BUTTON 来实现. 具体步骤 1.直接在按钮上加上onClick事件打开指定页面: &l ...

  3. 对于大批量赋值功能,使用if判断是否能提高性能

    场景: 如果对某变量进行赋值,是否需要判断一下,如果相等就不用赋值,这样会不会提高性能. 代码如下: "; "; , x2=, x3=; Stopwatch w = new Sto ...

  4. JavaScript笔记:对象及数组

    一.对象 在javascript中,对象是拥有属性和方法的一种基本数据类型 1.创建object 创建object实例有如下两种方式: 使用new操作符后跟object构造函数创建,如下代码: var ...

  5. C++ 随机数

    #include <iostream> #include <stdlib.h> #include <time.h> #define random(a,b) (ran ...

  6. JS操作JSON总结

    JSON(JavaScript Object Notation) 是一种轻量级的数据交换格式,采用完全独立于语言的文本格式,是理想的数据交换格式.同时,JSON是 JavaScript 原生格式,这意 ...

  7. “不是有效WIN32程序”

    写了个控制台,放到服务器上面运行,运行失败,出现"不是有效win32程序" 不知道原因. 猜测: 1.程序只支持64位的处理器,修改了项目的属性,发现支持any cpu.排除 2. ...

  8. 第六百一十八天 how can I 坚持

    此刻好烦,乱七八糟的,红米2死机也没弄好,哎. 下周三去长城,感觉还有很大提升空间啊,什么都不会.哎. 眼累的不行了,得抓紧睡觉了.ls他们来北京开年会了.. 明天,zjp来找我玩呢. 睡觉了.累.

  9. java后端书籍推荐

    书架主要针对Java后端开发. 3.0版把一些后来买的.看的书添补进来,又或删掉或降级一些后来没有再翻开过的书. 更偏爱那些能用简短流畅的话,把少壮不努力的程序员所需的基础补回来的薄书,而有些教课书可 ...

  10. WinForm窗体嵌入

    一.在winform窗体上添加两个控件 1.容器>Panel 2.添加 SideBar.dll (下载链接:http://pan.baidu.com/s/1o6qhf9w) (1)将SideBa ...