微信扫码支付功能(2)---用户扫码支付成功,微信异步回调商户接口

用户扫码支付成功,微信异步回调商户

上一篇博客完成用户扫码支付功能: https://www.cnblogs.com/qdhxhz/p/9708534.html

当用户扫码支付成功之后,微信会异步回调商户接口,告知用户支付成功。好让商户进行下一步操作。

一、接口说明

1、流程图

这里要做的就是用户支付成功后,微信异步通知商户支付结果,商户收到通知后告知支付通知接收情况。

2、接口说明

有关商户接口应注意以下几点:

(1)该链接是通过【统一下单API】中提交的参数notify_url设置,如果链接无法访问,商户将无法接收到微信通知。

(2)notify_url不能有参数,外网可以直接访问,不能有访问控制(比如必须要登录才能操作)。示例:notify_url:“https://pay.weixin.qq.com/wxpay/pay.action”

(3)支付完成后,微信会把相关支付结果和用户信息发送给商户,商户需要接收处理,并返回应答。

(4)对后台通知交互时,如果微信收到商户的应答不是成功或超时,微信认为通知失败,微信会通过一定的策略定期重新发起通知,尽可能提高通知的成功率,但微信不

保证通知最终能成功。(通知频率为15/15/30/180/1800/1800/1800/1800/3600,单位:秒)注意:同样的通知可能会多次发送给商户系统。商户系统必须能够正确处理

重复的通知。推荐的做法是,当收到通知进行处理时,首先检查对应业务数据的状态,判断该通知是否已经处理过,如果没有处理过再进行处理,如果处理过直接返回结果成功。

在对业务数据进行状态检查和处理之前,要采用数据锁进行并发控制,以避免函数重入造成的数据混乱。

(5)特别提醒:商户系统对于支付结果通知的内容一定要做签名验证,防止数据泄漏导致出现“假通知”,造成资金损失。

二、接口开发

1、回调接口

有关ngrok工具如果不了解的话,可以参考博客:   https://www.cnblogs.com/qdhxhz/p/9678137.html

    /**
     * 微信支付回调
     * 这里在统一下单中提供的notify_url地址是:http://jincou.vipgz1.idcfengye.com/api/v1/order/callback
     * 该域名是sunny-ngrok中的二级域名,通过它映射到微信本地
     */
    @RequestMapping("callback")
    public void orderCallback(HttpServletRequest request,HttpServletResponse response) throws Exception {
        InputStream inputStream =  request.getInputStream();
        //BufferedReader是包装设计模式,性能更搞
        BufferedReader in =  new BufferedReader(new InputStreamReader(inputStream,"UTF-8"));
        StringBuffer sb = new StringBuffer();
        //1、将微信回调信息转为字符串
        String line ;
        while ((line = in.readLine()) != null){
            sb.append(line);
        }
        in.close();
        inputStream.close();
        //2、将xml格式字符串格式转为map集合
        Map<String,String> callbackMap = WXPayUtil.xmlToMap(sb.toString());
        System.out.println(callbackMap.toString());
        //3、转为有序的map
        SortedMap<String,String> sortedMap = WXPayUtil.getSortedMap(callbackMap);
        //4、判断签名是否正确
        if(WXPayUtil.isCorrectSign(sortedMap,weChatConfig.getKey())){
            //5、判断回调信息是否成功
            if("SUCCESS".equals(sortedMap.get("result_code"))){
                //获取商户订单号
                //商户系统内部订单号,要求32个字符内,只能是数字、大小写字母_-|* 且在同一个商户号下唯一
                String outTradeNo = sortedMap.get("out_trade_no");
                System.out.println(outTradeNo);
                //6、数据库查找订单,如果存在则根据订单号更新该订单
                VideoOrder dbVideoOrder = videoOrderService.findByOutTradeNo(outTradeNo);
                System.out.println(dbVideoOrder);
                if(dbVideoOrder != null && dbVideoOrder.getState()==0){  //判断逻辑看业务场景
                    VideoOrder videoOrder = new VideoOrder();
                    videoOrder.setOpenid(sortedMap.get("openid"));
                    videoOrder.setOutTradeNo(outTradeNo);
                    videoOrder.setNotifyTime(new Date());
                    //修改支付状态,之前生成的订单支付状态是未支付,这里表面已经支付成功的订单
                    videoOrder.setState(1);
                    //根据商户订单号更新订单
                    int rows = videoOrderService.updateVideoOderByOutTradeNo(videoOrder);
                    System.out.println(rows);
                    //7、通知微信订单处理成功
                    if(rows == 0){
                        response.setContentType("text/xml");
                        response.getWriter().println("success");
                        return;
                    }
                }}
        }
        //7、通知微信订单处理失败
        response.setContentType("text/xml");
        response.getWriter().println("fail");

    }

2、校验签名方法

    /**
     * 校验签名
     */
    public static boolean isCorrectSign(SortedMap<String, String> params, String key){

        //1、再进行一次生成sign
        String sign = createSign(params,key);
        String weixinPaySign = params.get("sign").toUpperCase();
        //将两次生成的sign比较看是否一致
        return weixinPaySign.equals(sign);
    }

    /**
     * 生成微信支付sign
     */
    public static String createSign(SortedMap<String, String> params, String key){
        StringBuilder sb = new StringBuilder();
        Set<Map.Entry<String, String>> es =  params.entrySet();
        Iterator<Map.Entry<String,String>> it =  es.iterator();
        //生成 stringA="appid=wxd930ea5d5a258f4f&body=test&device_info=1000&mch_id=10000100&nonce_str=ibuaiVcKdpRxkhJA";
        while (it.hasNext()){
            Map.Entry<String,String> entry = (Map.Entry<String,String>)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=").append(key);
        String sign = CommonUtils.MD5(sb.toString()).toUpperCase();
        return sign;
    }

3、测试

(1)支付成功

(2)通过ngrok回调到本地,通过断点可以看出sb字符串格式

(3)将xml格式字符串转为map

成功!

github源码

githubhttps://github.com/yudiandemingzi/wechatpay

我只是偶尔安静下来,对过去的种种思忖一番。那些曾经的旧时光里即便有过天真愚钝,也不值得谴责。毕竟,往后的日子,还很长。不断鼓励自己,

天一亮,又是崭新的起点,又是未知的征程(上校17)

原文地址:https://www.cnblogs.com/qdhxhz/p/9716216.html

时间: 2024-10-13 00:34:30

微信扫码支付功能(2)---用户扫码支付成功,微信异步回调商户接口的相关文章

VS.NET NET4.0 C#.NET微信公众平台源码,功能齐全 微信源码

C#.NET微信公众平台源码,功能齐全 微信源码 会员卡,微商城,微营销等等 源码已集成目前市场主流功能,并实时更新,应用商店更有大量贴心/实用/酷炫功能和模板可供自主添加 演示地址http://cx010108.pssdss.com/admin/ 用户名 admin 密码 529 源码下载http://www.pssdss.com/d230.html 更多源码网站http://www.pssdss.com 联系QQ:11851298

ASP.NET Core Web 支付功能接入 支付宝-电脑网页支付篇

这篇文章将介绍ASP.NET Core中使用 开源项目 Payment,实现接入支付宝-电脑网页支付接口及同步跳转及异步通知功能. 开发环境:Win 10 x64.VS2017 15.6.4..NET Core SDK 2.1.101..NET Core Runtime 2.0.6 1.新建"ASP.NET Core Web 应用程序"项目,我将它命名为AlipaySample. 2. 引入安装Nuget包 "Essensoft.AspNetCore.Alipay"

微信扫码支付功能(1)---通过谷歌二维码工具生成付款码

生成付款二维码 一.微信网站扫码支付介绍 1.扫码支付文档 微信开发官方文档:https://pay.weixin.qq.com/wiki/doc/api/native.php?chapter=6_5 有关微信支付的流程图微信官方已经说的很清楚了,这里也无需其它解释.这边采用微信支付扫码模式二(不依赖商户平台设置回调url),所以在生成二维码之前 要先调用微信统一下单支付接口,获得code_url,再通过谷歌二维码工具将code_url生成二维码图片. 2.名称理解 在微信扫码支付功能开发之前,

如何玩转微信支付功能的原理和开发(转)

打开微信,各种营销信息霸占了我的眼球,以“微信支付+微信小店”的模式挑战阿里“支付宝+淘宝天猫”的模式开启了新纪元,腾讯此举是在革淘宝的命吗?有人说,微信对阿里最大的挑战,是把连接能力下发给了企业/用户,让企业/用户而不是平台自身发挥主动权和能动性来建立新的连接模式. 近年来,移动支付发展迅猛,移动支付已经成为了不可抵挡的发展趋势,其引领了新一轮的支付潮流.从某种角度来讲,反观移动互联网的迅速发展,对微信的快速发展起到了很大的推动力,其所蕴含的巨大潜力使其成为了市场争相抢夺的香饽饽.一时间各种支

微信小程序 使用微信支付功能实现在线支付订单

以前做过PC页面微信支付,但是这次在小程序 直接调用微信支付功能还是方便很多 先放个微信官方API链接:https://pay.weixin.qq.com/wiki/doc/api/wxa/wxa_api.php?chapter=7_7&index=5 先说说整个下单支付流程的整体思路, 0,准备工作: 一,appId,开发帐号中注册时的appId. 二,sdkContent,后台返回的包含有金额,支付方式等信息的数据包. 三,key值,商户申请微信支付功能时所配置的密钥 准备好后, 1,首先选

谈谈开发支付功能碰到的坑

文章原创于公众号:程序猿周先森.本平台不定时更新,喜欢我的文章,欢迎关注我的微信公众号. 最近因为有了新的需求,需要开发支付宝支付功能以及微信支付功能,两三天开发下来碰到了几个Bug,在这里记录下来以供以后可以温故知新.因为支付宝功能是在H5端进行使用,所以使用了支付宝扫码付功能,生成一张支付二维码,然后用户保存二维码去支付宝进行扫码支付操作.一路磕磕碰碰把功能完善出来了,但是碰到了几个坑.支付宝支付开发碰到的问题: 1.无效的APP_ID 这个问题其实是最容易犯的一个错误,因为支付宝支付功能有

微信公众平台开发(86) 获取用户基本信息

本文介绍在微信公众平台上如何使用高级接口开发获取用户基本信息的功能. 一.获取用户基本信息接口 在关注者与公众号产生消息交互后,公众号可获得关注者的OpenID(加密后的微信号,每个用户对每个公众号的OpenID是唯一的.对于不同公众号,同一用户的openid不同).公众号可通过本接口来根据OpenID获取用户基本信息,包括昵称.头像.性别.所在城市.语言和关注时间. 获取用户基本信息 开发者可通过OpenID来获取用户基本信息.请使用https协议. 接口调用请求说明 http请求方式: GE

在线支付功能的设计及其实现

----------------------------------------------------------------------------------------------[版权申明:本文系作者原创,转载请注明出处] 文章出处:http://blog.csdn.net/sdksdk0/article/details/52154672作者:朱培      ID:sdksdk0      邮箱: [email protected]   ------------------------

微信支付接口开发之---微信支付之JSSDK(公众号支付)步骤

1.准备 1.1.公众号为服务号,开通微信支付功能 1.2.为了方便调试微信后台的回调URL(必须为外网),我用了nat123软件来做一个映射 1.3.官方微信开发的示例WxPayApi(.net版本) 2.业务流程图 3.步骤 3.1.用户访问商户的链接,商户链接地址调用[网页授权获取用户信息]接口获取用户的openid和access_token 参考:网页授权获取用户基本信息 3.1.1.第一步,用户同意授权,获取code,调用接口如下 https://open.weixin.qq.com/