微信、支付宝二码合一扫码支付实现思路
程序员文章站
2024-01-19 14:03:28
...
一、支付二维码(预订单)
根据需要购买的信息创建预订单,将订单信息保存到Redis中,并设置有效期,注意生产二维码的链接后的参数可以关联到Redis中的key;
QRCode 为servlet扫码请求的URL;
UUIDUtils.getUUID() 为预订单单号,在servlet请求中截取,然后在Redis中查找对应的Key的数据;
二维码地址:http://kung900519.qicp.io/interface/QRCode/UUIDUtils.getUUID();
二、创建二维码扫码请求地址servlet:QRCodeServlet;微信支付重定向请求servlet:WechatPayServlet;支付宝重定向请求servlet:AliPayServlet;
QRCodeServlet 用于用户使用微信或者支付宝扫码二维码进行客户端识别及重定向到对应的业务处理;
package com.platform.cloudlottery.servlet;
import java.io.IOException;
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.context.support.SpringBeanAutowiringSupport;
import com.platform.cloudlottery.common.CommonConfig;
import com.platform.cloudlottery.common.alipay.config.MyAliPayConfig;
import com.platform.cloudlottery.common.wechat.config.WXPublicConfig;
import com.platform.cloudlottery.common.wechat.util.HttpUtil;
import com.platform.cloudlottery.model.SysPayChannel;
import com.platform.cloudlottery.service.Impl.SysPayChannelServiceImpl;
import com.platform.cloudlottery.web.StatusContant.PayTypeConstant;
/**
* @ClassName: QRCodeServlet
* @Description: TODO(根据请求的后缀获取该数据编码对应的数据,并重定向到页面)
* @author chenkun
* @date 2018年12月29日
*
*/
public class QRCodeServlet extends HttpServlet {
private static final long serialVersionUID = -8457626626670970403L;
protected Logger logger = LoggerFactory.getLogger(getClass());
private static final String UrlStr = "QRCode/";
private static final String wechatPay = "wechatPay/";
private static final String aliPay = "aliPay/";
@Autowired
private SysPayChannelServiceImpl payChannelService;
public void init(ServletConfig servletConfig) throws ServletException {
super.init(servletConfig);
SpringBeanAutowiringSupport.processInjectionBasedOnServletContext(this, servletConfig.getServletContext());
}
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
logger.info("####################请求开始####################");
String userAgent = request.getHeader("user-agent");
String RequestURL = request.getRequestURL().toString();
logger.info("URL : " + RequestURL);
String ReqInfo = RequestURL.substring(RequestURL.indexOf(UrlStr)+UrlStr.length());
logger.info("URL : " + ReqInfo);
CommonConfig commonConfig = new CommonConfig();
if (userAgent != null && userAgent.contains("AlipayClient")) {
logger.info("来自支付宝");
String redirecturi = HttpUtil.urlEnCode(commonConfig.getDomain() + aliPay + ReqInfo);
logger.info("REDIRECT_URI="+redirecturi);
SysPayChannel channel = payChannelService.selectByChannelType(PayTypeConstant.Alipay);
MyAliPayConfig aliPayConfig = new MyAliPayConfig();
aliPayConfig.setAppId(channel.getAppid());
// 授权页面地址
String requestUrl = aliPayConfig.getAuthgateway();
requestUrl = requestUrl.replace("APPID", aliPayConfig.getAppId()).replace("SCOPE", aliPayConfig.getScope()).replace("REDIRECT_URI", redirecturi);
// 重定向到授权页面
response.sendRedirect(requestUrl);
} else if (userAgent != null && userAgent.contains("MicroMessenger")) {
logger.info("来自微信");
String redirecturi = HttpUtil.urlEnCode(commonConfig.getDomain() + wechatPay + ReqInfo);
logger.info("REDIRECT_URI="+redirecturi);
SysPayChannel channel = payChannelService.selectByChannelType(PayTypeConstant.Wechat);
WXPublicConfig publicConfig = new WXPublicConfig();
publicConfig.setAppId(channel.getAppid());
publicConfig.setOriginId(channel.getOriginid());
publicConfig.setAppSecret(channel.getAppsecret());
publicConfig.setEncodingAESKey(channel.getEncodingaeskey());
// 授权页面地址
String requestUrl = publicConfig.getAuthorizeinterface();
requestUrl = requestUrl.replace("APPID", publicConfig.getAppId()).replace("REDIRECT_URI", redirecturi).replace("SCOPE", publicConfig.getScope()).replace("STATE", publicConfig.getState());
// 重定向到授权页面
response.sendRedirect(requestUrl);
} else {
logger.info("未知来源");
}
logger.info("####################请求结束####################");
}
public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doGet(request, response);
}
}
WechatPayServlet 在获取到Redis中预订单数据后,创建真实订单并调用微信“统一下单接口”;
package com.platform.cloudlottery.servlet;
import java.io.IOException;
import java.util.Date;
import java.util.LinkedHashMap;
import java.util.Map;
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.context.support.SpringBeanAutowiringSupport;
import com.alibaba.fastjson.JSONObject;
import com.github.wxpay.sdk.WXPayUtil;
import com.platform.cloudlottery.common.CommonConfig;
import com.platform.cloudlottery.common.jedis.JedisUtil;
import com.platform.cloudlottery.common.lang.StringUtils;
import com.platform.cloudlottery.common.wechat.bean.WeiXinOAuth2Token;
import com.platform.cloudlottery.common.wechat.bean.WeiXinUserInfo;
import com.platform.cloudlottery.common.wechat.config.WXPayConfig;
import com.platform.cloudlottery.common.wechat.config.WXPublicConfig;
import com.platform.cloudlottery.common.wechat.util.WeiXinOAuth2Util;
import com.platform.cloudlottery.common.wechat.util.WeiXinPayUtils;
import com.platform.cloudlottery.model.SysPayChannel;
import com.platform.cloudlottery.service.OrderServcie;
import com.platform.cloudlottery.service.UserInfoService;
import com.platform.cloudlottery.service.Impl.LotteryOrderServiceImpl;
import com.platform.cloudlottery.service.Impl.SysPayChannelServiceImpl;
import com.platform.cloudlottery.service.Impl.UserMemberServiceImpl;
import com.platform.cloudlottery.common.utils.BusinessCodeUtils;
import com.platform.cloudlottery.web.StatusContant.PayTypeConstant;
import com.platform.cloudlottery.web.SysKey;
import redis.clients.jedis.Jedis;
/**
* @ClassName: WechatPayServlet
* @Description: TODO(这里用一句话描述这个类的作用)
* @author chenkun
* @date 2019年1月5日
*
*/
public class WechatPayServlet extends HttpServlet {
private static final long serialVersionUID = -8457626626670970403L;
protected Logger logger = LoggerFactory.getLogger(getClass());
// 请求路径包含的字符串
private static final String UrlStr = "wechatPay/";
@Autowired
private SysPayChannelServiceImpl payChannelService;
@Autowired
private UserMemberServiceImpl memberService;
@Autowired
private LotteryOrderServiceImpl lotteryOrderService;
public void init(ServletConfig servletConfig) throws ServletException {
super.init(servletConfig);
SpringBeanAutowiringSupport.processInjectionBasedOnServletContext(this, servletConfig.getServletContext());
}
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
logger.info("####################请求开始####################");
request.setCharacterEncoding("utf-8");
response.setCharacterEncoding("utf-8");
try {
// 用户同意授权后,能获取到code
String code = request.getParameter("code");
// 用户同意授权
if (!"authdeny".equals(code)) {
SysPayChannel channel = payChannelService.selectByChannelType(PayTypeConstant.Wechat);
WXPublicConfig publicConfig = new WXPublicConfig();
publicConfig.setAppId(channel.getAppid());
publicConfig.setOriginId(channel.getOriginid());
publicConfig.setAppSecret(channel.getAppsecret());
publicConfig.setEncodingAESKey(channel.getEncodingaeskey());
WXPayConfig payConfig = new WXPayConfig();
payConfig.setMchId(channel.getMchid());
payConfig.setAppId(channel.getAppid());
payConfig.setKey(channel.getWxkey());
payConfig.setApicertPath(channel.getPayCertUrl());
payConfig.setSpbillCreateIp(channel.getSpbillcreateip());
// 获取网页授权access_token
WeiXinOAuth2Token weixinOauth2Token = WeiXinOAuth2Util.getOAuth2AccessToken(publicConfig,code);
// 网页授权接口访问凭证
String accessToken = weixinOauth2Token.getAccessToken();
logger.info("accessToken=" + accessToken);
// 用户标识
String openId = weixinOauth2Token.getOpenId();
logger.info("openId="+openId);
// 获取用户信息
WeiXinUserInfo userInfo = WeiXinOAuth2Util.getOAuth2UserInfo(publicConfig, accessToken, openId);
logger.info(userInfo.getNickName()+"=====微信支付====="+userInfo.getOpenId());
//添加或更新用户信息
String userid = UserInfoService.CreateUserMember(userInfo,memberService);
String RequestURL = request.getRequestURL().toString();
logger.info("URL : " + RequestURL);
String QRCodeReqInfo = RequestURL.substring(RequestURL.indexOf(UrlStr) + UrlStr.length());
logger.info("URL : " + QRCodeReqInfo);
CommonConfig commonConfig = new CommonConfig();
Jedis redis = JedisUtil.getJedis();
String advancekey = commonConfig.getLotteryorder() + QRCodeReqInfo;
if (redis.exists(advancekey)) {// 判断key是否存在
if (!StringUtils.trimToEmpty(redis.get(advancekey)).equals("")) {
JSONObject jsonObject = JSONObject.parseObject(redis.get(advancekey));
if (null != jsonObject) {
if (redis.get(advancekey + "_lock") == null || redis.get(advancekey + "_lock").equals("")){
redis.setex(advancekey + "_lock", 1, "lock");
String orderid = BusinessCodeUtils.getOrderNo(jsonObject.getString(SysKey.deviceSn));
int money = jsonObject.getIntValue(SysKey.money);
int lotterytype = jsonObject.getIntValue(SysKey.lotteryType);
if (!orderid.equals("") && money!=0) {
//创建订单
boolean bool = OrderServcie.createorder(QRCodeReqInfo, PayTypeConstant.Wechat, payConfig.getAppID(), userid, openId, orderid, jsonObject, lotteryOrderService);
if (bool) {
//删除预订单信息
redis.del(advancekey);//一个预订单只能创建一个订单
String paymoney = String.valueOf(money);
if (!commonConfig.isProduction()) {//测试环境
paymoney = "30";
}
logger.debug("是否生产环境:"+commonConfig.isProduction()+";订单金额为:"+String.valueOf(money)+";实际支付金额为:"+paymoney);
//创建微信订单
Map<String, String> map = WeiXinPayUtils.createOrderJsapi(payConfig, orderid, paymoney, lotterytype==0?"即开票":"电脑票", openId);
logger.info("创建微信支付预订单返回数据:"+JSONObject.toJSONString(map));
if (map != null) {
if (map.get("return_code").equals("SUCCESS")) {
if (map.get("result_code").equals("SUCCESS")) {
logger.info("创建微信支付预订单成功");
Map<String, String> data = new LinkedHashMap<String, String>();
data.put("appId", payConfig.getAppID());
data.put("timeStamp", String.valueOf(new Date().getTime()/1000));
data.put("nonceStr", WXPayUtil.generateNonceStr());
data.put("package", "prepay_id="+map.get("prepay_id"));
data.put("signType", "MD5");
data.put("paySign", WXPayUtil.generateSignature(data, payConfig.getKey()));
logger.info("返回到客户端的数据:"+JSONObject.toJSONString(data));
request.setAttribute("appId", data.get("appId"));
request.setAttribute("timeStamp", data.get("timeStamp"));
request.setAttribute("nonceStr", data.get("nonceStr"));
request.setAttribute("package", data.get("package"));
request.setAttribute("signType", data.get("signType"));
request.setAttribute("paySign", data.get("paySign"));
request.getRequestDispatcher("../pay/WechatPay.jsp").forward(request, response);
}else{
logger.info("创建订单失败: 创建支付预订单失败");
request.setAttribute("message", "创建订单失败");
request.getRequestDispatcher("../pay/WechatPayFail.jsp").forward(request, response);
}
} else {
logger.info("创建订单失败:创建支付预订单失败");
request.setAttribute("message", "创建订单失败");
request.getRequestDispatcher("../pay/WechatPayFail.jsp").forward(request, response);
}
} else {
logger.info("创建订单失败:创建支付预订单失败");
request.setAttribute("message", "创建订单失败");
request.getRequestDispatcher("../pay/WechatPayFail.jsp").forward(request, response);
}
} else {
logger.info("创建订单失败:创建支付预订单失败");
request.setAttribute("message", "创建订单失败");
request.getRequestDispatcher("../pay/WechatPayFail.jsp").forward(request, response);
}
} else {
logger.info("创建订单失败;订单金额或者订单号数据有误");
request.setAttribute("message", "创建订单失败");
request.getRequestDispatcher("../pay/WechatPayFail.jsp").forward(request, response);
}
} else {
logger.info("二维码失效");
request.setAttribute("message", "二维码失效");
request.getRequestDispatcher("../pay/WechatPayFail.jsp").forward(request, response);
}
} else {
logger.info("二维码失效");
request.setAttribute("message", "二维码失效");
request.getRequestDispatcher("../pay/WechatPayFail.jsp").forward(request, response);
}
} else {
logger.info("二维码失效");
request.setAttribute("message", "二维码失效");
request.getRequestDispatcher("../pay/WechatPayFail.jsp").forward(request, response);
}
} else {
logger.info("二维码失效");
request.setAttribute("message", "二维码失效");
request.getRequestDispatcher("../pay/WechatPayFail.jsp").forward(request, response);
}
}
} catch (Exception e) {
e.printStackTrace();
logger.info("系统异常");
request.setAttribute("message", "二维码失效");
request.getRequestDispatcher("../pay/WechatPayFail.jsp").forward(request, response);
}
logger.info("####################请求结束####################");
}
public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doGet(request, response);
}
}
AliPayServlet 在获取到Redis中预订单数据后,创建真实订单并调用支付宝“手机网站支付接口”;
package com.platform.cloudlottery.servlet;
import java.io.IOException;
import java.math.BigDecimal;
import java.util.Properties;
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.context.support.SpringBeanAutowiringSupport;
import com.alibaba.fastjson.JSONObject;
import com.platform.cloudlottery.common.CommonConfig;
import com.platform.cloudlottery.common.alipay.bean.AliPayOAuth2Token;
import com.platform.cloudlottery.common.alipay.bean.AliPayUserInfo;
import com.platform.cloudlottery.common.alipay.config.MyAliPayConfig;
import com.platform.cloudlottery.common.alipay.uitl.AliPayOAuth2Util;
import com.platform.cloudlottery.common.alipay.uitl.AlipayPayUtils;
import com.platform.cloudlottery.common.jedis.JedisUtil;
import com.platform.cloudlottery.common.lang.StringUtils;
import com.platform.cloudlottery.common.properties.PropertiesUtils;
import com.platform.cloudlottery.model.SysPayChannel;
import com.platform.cloudlottery.service.OrderServcie;
import com.platform.cloudlottery.service.UserInfoService;
import com.platform.cloudlottery.service.Impl.LotteryOrderServiceImpl;
import com.platform.cloudlottery.service.Impl.SysPayChannelServiceImpl;
import com.platform.cloudlottery.service.Impl.UserMemberServiceImpl;
import com.platform.cloudlottery.common.utils.BusinessCodeUtils;
import com.platform.cloudlottery.web.StatusContant.PayTypeConstant;
import com.platform.cloudlottery.web.SysKey;
import redis.clients.jedis.Jedis;
/**
* @ClassName: AliPayServlet
* @Description: TODO(这里用一句话描述这个类的作用)
* @author chenkun
* @date 2019年1月5日
*
*/
public class AliPayServlet extends HttpServlet {
private static final long serialVersionUID = -8457626626670970403L;
protected Logger logger = LoggerFactory.getLogger(getClass());
// 请求路径包含的字符串
private static final String UrlStr = "aliPay/";
@Autowired
private SysPayChannelServiceImpl payChannelService;
@Autowired
private UserMemberServiceImpl memberService;
@Autowired
private LotteryOrderServiceImpl lotteryOrderService;
public void init(ServletConfig servletConfig) throws ServletException {
super.init(servletConfig);
SpringBeanAutowiringSupport.processInjectionBasedOnServletContext(this, servletConfig.getServletContext());
}
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
logger.info("####################请求开始####################");
request.setCharacterEncoding("utf-8");
response.setCharacterEncoding("utf-8");
try {
//用户同意授权后,能获取到code
String code = request.getParameter("auth_code");
//用户同意授权
if (!code.equals("")) {
SysPayChannel channel = payChannelService.selectByChannelType(PayTypeConstant.Alipay);
MyAliPayConfig aliPayConfig = new MyAliPayConfig();
aliPayConfig.setAppId(channel.getAppid());
String certsrc = channel.getPayCertUrl();
Properties propertiesFile = PropertiesUtils.getPropertiesFile(certsrc);
if (propertiesFile != null) {
aliPayConfig.setPayeeAccount(propertiesFile.getProperty("ALI_PAYEE_ACCOUNT"));
aliPayConfig.setAppId(propertiesFile.getProperty("ALI_APP_ID"));
aliPayConfig.setAliPayPublicKey(propertiesFile.getProperty("ALI_ALIPAY_PUBLIC_KEY"));
aliPayConfig.setAppPayPublicKey(propertiesFile.getProperty("ALI_APP_PAY_PUBLIC_KEY"));
aliPayConfig.setAppPrivateKey(propertiesFile.getProperty("ALI_APP_PRIVATE_KEY"));
}
//获取网页授权access_token
AliPayOAuth2Token aliPayOAuth2Token = AliPayOAuth2Util.getOAuth2AccessToken(aliPayConfig,code);
//网页授权接口访问凭证
String accessToken = aliPayOAuth2Token.getAccessToken();
logger.info("accessToken=" + accessToken);
//用户标识
String aliuserid = aliPayOAuth2Token.getUserid();
logger.info("aliuserid="+aliuserid);
//获取用户信息
AliPayUserInfo userInfo = AliPayOAuth2Util.getOAuth2UserInfo(aliPayConfig,accessToken,aliuserid);
logger.info(userInfo.getNickName()+"=====支付宝支付====="+userInfo.getUserId());
//添加或更新用户信息
String userid = UserInfoService.CreateUserMember(userInfo,memberService);
//具体业务
String RequestURL = request.getRequestURL().toString();
logger.info("URL : " + RequestURL);
String QRCodeReqInfo = RequestURL.substring(RequestURL.indexOf(UrlStr) + UrlStr.length());
logger.info("URL : " + QRCodeReqInfo);
CommonConfig commonConfig = new CommonConfig();
Jedis redis = JedisUtil.getJedis();
String advancekey = commonConfig.getLotteryorder() + QRCodeReqInfo;
if (redis.exists(advancekey)) {// 判断key是否存在
if (!StringUtils.trimToEmpty(redis.get(advancekey)).equals("")) {
JSONObject jsonObject = JSONObject.parseObject(redis.get(advancekey));
if (null != jsonObject) {
if (redis.get(advancekey + "_lock") == null || redis.get(advancekey + "_lock").equals("")){
redis.setex(advancekey + "_lock", 1, "lock");
String orderid = BusinessCodeUtils.getOrderNo(jsonObject.getString(SysKey.deviceSn));
int money = jsonObject.getIntValue(SysKey.money);
int lotterytype = jsonObject.getIntValue(SysKey.lotteryType);
if (!orderid.equals("") && money != 0) {
//创建订单
boolean bool = OrderServcie.createorder(QRCodeReqInfo, PayTypeConstant.Alipay, aliPayConfig.getAppId(), userid, aliuserid, orderid, jsonObject, lotteryOrderService);
if (bool) {
//删除预订单信息
redis.del(advancekey);//一个预订单只能创建一个订单
String paymoney = BigDecimal.valueOf(Long.valueOf(money)).divide(new BigDecimal(100)).toString();
if (!commonConfig.isProduction()) {//测试环境
paymoney = "0.30";
}
logger.debug("是否生产环境:"+commonConfig.isProduction()+";订单金额为:"+BigDecimal.valueOf(Long.valueOf(money)).divide(new BigDecimal(100)).toString()+";实际支付金额为:"+paymoney);
//创建支付宝订单
String responsestr = AlipayPayUtils.createOrderWapPay(aliPayConfig, orderid, lotterytype==0?"即开票":"电脑票", paymoney, "");
logger.info("创建支付宝支付预订单返回数据:"+responsestr);
if (!responsestr.equals("")) {
response.setContentType("text/html;charset=UTF-8");
response.getWriter().write(responsestr);//直接将完整的表单html输出到页面
response.getWriter().flush();
response.getWriter().close();
response.getWriter().append("Served at: ").append(request.getContextPath());
} else {
logger.info("创建订单失败:创建支付预订单失败");
request.setAttribute("message", "创建订单失败");
request.getRequestDispatcher("../pay/AliPayFail.jsp").forward(request, response);
}
} else {
logger.info("创建订单失败:创建支付预订单失败");
request.setAttribute("message", "创建订单失败");
request.getRequestDispatcher("../pay/AliPayFail.jsp").forward(request, response);
}
} else {
logger.info("创建订单失败;订单金额或者订单号数据有误");
request.setAttribute("message", "创建订单失败");
request.getRequestDispatcher("../pay/AliPayFail.jsp").forward(request, response);
}
} else {
logger.info("二维码失效");
request.setAttribute("message", "二维码失效");
request.getRequestDispatcher("../pay/AliPayFail.jsp").forward(request, response);
}
} else {
logger.info("二维码失效");
request.setAttribute("message", "二维码失效");
request.getRequestDispatcher("../pay/AliPayFail.jsp").forward(request, response);
}
} else {
logger.info("二维码失效");
request.setAttribute("message", "二维码失效");
request.getRequestDispatcher("../pay/AliPayFail.jsp").forward(request, response);
}
} else {
logger.info("二维码失效");
request.setAttribute("message", "二维码失效");
request.getRequestDispatcher("../pay/AliPayFail.jsp").forward(request, response);
}
}
} catch (Exception e) {
e.printStackTrace();
logger.info("系统异常");
request.setAttribute("message", "二维码失效");
request.getRequestDispatcher("../pay/AliPayFail.jsp").forward(request, response);
}
logger.info("####################请求结束####################");
}
public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doGet(request, response);
}
}
三、创建微信支付结果回调接口和支付宝支付接口回调接口,用于接收微信或者支付宝的支付结果通知;
aliPayNotify 支付宝支付成功回调接口
/**
* @Title: aliPayNotify
* @Description: TODO(支付宝支付成功过回调)
* @author chenkun
* @return 参数
* @return String 返回类型
* @throws
*/
@RequestMapping(value = "/aliPayNotify", method = RequestMethod.POST)
public String aliPayNotify() {
ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
HttpServletRequest request = attributes.getRequest();
Map<String, String> params = convertRequestParamsToMap(request); // 将异步通知中收到的待验证所有参数都存放到map中
String paramsJson = JSON.toJSONString(params);
logger.info("支付宝支付回调,{" + paramsJson + "}");
try {
SysPayChannel channel = payChannelService.selectByChannelType(PayTypeConstant.Alipay);
MyAliPayConfig aliPayConfig = new MyAliPayConfig();
aliPayConfig.setAppId(channel.getAppid());
String certsrc = channel.getPayCertUrl();
Properties propertiesFile = PropertiesUtils.getPropertiesFile(certsrc);
if (propertiesFile != null) {
aliPayConfig.setPayeeAccount(propertiesFile.getProperty("ALI_PAYEE_ACCOUNT"));
aliPayConfig.setAppId(propertiesFile.getProperty("ALI_APP_ID"));
aliPayConfig.setAliPayPublicKey(propertiesFile.getProperty("ALI_ALIPAY_PUBLIC_KEY"));
aliPayConfig.setAppPayPublicKey(propertiesFile.getProperty("ALI_APP_PAY_PUBLIC_KEY"));
aliPayConfig.setAppPrivateKey(propertiesFile.getProperty("ALI_APP_PRIVATE_KEY"));
}
// 调用SDK验证签名
boolean signVerified = AlipaySignature.rsaCheckV1(params, aliPayConfig.getAliPayPublicKey(),
aliPayConfig.getCharset(), aliPayConfig.getSigntype());
if (signVerified) {
logger.info("支付宝回调签名认证成功");
// 按照支付结果异步通知中的描述,对支付结果中的业务内容进行1\2\3\4二次校验,校验成功后在response中返回success,校验失败返回failure
this.check(params);
// 另起线程处理业务
executorService.execute(new AliPayNotifyTask(params,payCallBackService));
// 如果签名验证正确,立即返回success,后续业务另起线程单独处理
// 业务处理失败,可查看日志进行补偿,跟支付宝已经没多大关系。
return "success";
} else {
logger.info("支付宝回调签名认证失败,signVerified=false, paramsJson:{}", paramsJson);
return "failure";
}
} catch (AlipayApiException e) {
logger.error("支付宝回调签名认证失败,paramsJson:{},errorMsg:{}", paramsJson, e.getMessage());
return "failure";
}
}
WechatPayNotify 微信支付成功回调
/**
* @Title: WechatPayNotify
* @Description: TODO(微信支付成功回调)
* @author chenkun
* @return 参数
* @return String 返回类型
* @throws
*/
@RequestMapping(value = "/WechatPayNotify", method = RequestMethod.POST)
public String WechatPayNotify() {
ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
HttpServletRequest request = attributes.getRequest();
String result = "";// 返回给微信的处理结果
String notityXml = "";// 微信给返回的东西
String inputLine;
try {
while ((inputLine = request.getReader().readLine()) != null) {
notityXml += inputLine;
}
request.getReader().close();
} catch (Exception e) {
logger.error("微信支付回调失败,paramsJson:{},errorMsg:{}", "回调数据获取失败", e.getMessage());
result = setXml("fail", "xml获取失败");
e.printStackTrace();
}
if (StringUtils.isEmpty(notityXml)) {
logger.info("微信支付回调失败:回调数据为空");
result = setXml("fail", "xml为空");
}
try {
logger.info("微信支付回调数据:{" + notityXml + "}");
Map<String, String> map = WXPayUtil.xmlToMap(notityXml);
String result_code = (String) map.get("result_code");// 业务结果
String return_code = (String) map.get("return_code");// SUCCESS/FAIL
// 解析各种数据
if (result_code.equals("SUCCESS")) {
result = setXml("SUCCESS", "OK");
} else {
logger.info("微信返回的交易状态不正确(result_code=" + result_code + ")");
result = setXml("fail", "微信返回的交易状态不正确(result_code=" + result_code + ")");
}
// 如果微信返回的结果是success,则修改订单状态
if (return_code.equals("SUCCESS")) {
// 这里是我的业务........................................
String sr = payCallBackService.confirmWechatPayOrder(map,true);
logger.debug(sr);
if (StringUtils.isNotEmpty(sr)){
result = setXml("fail",sr);
executorService.execute(new WechatPayRefundTask(map,payCallBackService));
} else {
result = setXml("SUCCESS", "OK");
}
} else {
result = setXml("fail", return_code);
}
} catch (Exception e) {
logger.error("微信支付回调失败,paramsJson:{},errorMsg:{}", "回调数据处理失败", e.getMessage());
result = setXml("fail", "回调数据处理失败");
e.printStackTrace();
}
logger.info("回调成功----返回给微信的xml:" + result);
return result;
}
四、如果觉得有用,请通过邮箱([email protected])联系我,大家沟通交流,互相学习;