Java对接第三方支付渠道之支付宝支付
提示:支付宝相对于微信支付更人性化,且细节做得更好。
Java对接第三方支付渠道之支付宝支付
- 一、前期准备工作
- 二、导入依赖
- 三、书写配置类
- 四、书写配置文件
- 五、调用相关支付接口
- 1.流程图
- 2.创建支付
- 3.支付通知
- 4.查询支付
- 5.取消支付
- 总结
一、前期准备工作
支付宝支付分为正式环境和沙箱环境,我这里使用的是正式环境。
沙箱环境和正式环境差距不是很大,唯一的差距就是正式环境需要营业执照。沙箱环境就可以很好避免这个问题。
- 创建应用
- 绑定应⽤
- 配置秘钥
- 上线应⽤
- 签约功能
官方API文档地址: https://opendocs.alipay.com/open/270/01didh?ref=api
二、导入依赖
<!--支付宝sdk--><dependency><groupId>com.alipay.sdk</groupId><artifactId>alipay-sdk-java</artifactId><version>4.23.0.ALL</version></dependency>
三、书写配置类
/*** description:支付宝支付配置类* author:maozl* date:2022/8/1*/
@Configuration
@PropertySource("classpath:alipay.properties") //读取配置文件
@ConfigurationProperties(prefix="alipay") //读取wxpay节点
@Data //使用set方法将alipay节点中的值填充到当前类的属性中
@Slf4j
public class AliPayClientConfig {/*** APPID*/private String appId;/*** 商户PID*/private String sellerId;/*** 支付宝网关*/private String gatewayUrl;/*** 商户私钥*/private String merchantPrivateKey;/*** 支付宝公钥*/private String aliPayPublicKey;/*** 接口加密秘钥*/private String contentKey;/*** 页面跳转同步通知页面路径*/private String returnUrl;/*** 回调地址*/private String notifyUrl;@Beanpublic AlipayClient alipayClient() throws AlipayApiException {AlipayConfig alipayConfig=new AlipayConfig();//设置appIdalipayConfig.setAppId(appId);//设置商户私钥alipayConfig.setPrivateKey(merchantPrivateKey);//设置支付宝公钥alipayConfig.setAlipayPublicKey(aliPayPublicKey);//设置支付宝网关alipayConfig.setServerUrl(gatewayUrl);//设置请求格式,固定值json.alipayConfig.setFormat(AlipayConstants.FORMAT_JSON);//设置字符集alipayConfig.setCharset(AlipayConstants.CHARSET_UTF8);//设置签名类型alipayConfig.setSignType(AlipayConstants.SIGN_TYPE_RSA2);//构造clientAlipayClient alipayClient=new DefaultAlipayClient(alipayConfig);return alipayClient;}}
四、书写配置文件
# 支付宝支付相关参数# 应用ID,你的APPID
alipay.app-id=# 商户PID
alipay.seller-id=# 支付宝网关
alipay.gateway-url=# 商户私钥
alipay.merchant-private-key=# 支付宝公钥
aliPay.aliPay-public-key=# 接口内容加密秘钥,对称秘钥
alipay.content-key=# 页面跳转同步通知页面路径
alipay.return-url=# 支付宝支付成功回调地址
alipay.notify-url=
五、调用相关支付接口
1.流程图
2.创建支付
https://opendocs.alipay.com/apis/028r8t?scene=22
/*** 发起支付* @param orderNo* @param uid* @return*/@Overridepublic String createPay(String orderNo, String uid) {//根据orderNo获取orderInfoOrderInfo orderInfo = orderInfoService.getOne(new LambdaQueryWrapper<OrderInfo>().eq(OrderInfo::getOrderNo, orderNo).eq(OrderInfo::getUid, uid));if (Objects.isNull(orderInfo)){throw new ServiceErrorException(ResultCode.ERROR, "发起支付请求失败 - 订单不存在");}//更新订单的支付类型orderInfoService.updatePayTypeByOrderNo(orderInfo.getOrderNo(), PayType.ALIPAY);//创建支付宝请求对象AlipayTradePagePayRequest request=new AlipayTradePagePayRequest();//数据AlipayTradePagePayModel bizModel=new AlipayTradePagePayModel();bizModel.setOutTradeNo(orderInfo.getOrderNo());//单位是元bizModel.setTotalAmount(orderInfo.getTotalFee().toString());bizModel.setSubject(orderInfo.getTitle());//默认的bizModel.setProductCode("FAST_INSTANT_TRADE_PAY");request.setBizModel(bizModel);request.setNotifyUrl(aliPayClientConfig.getNotifyUrl());//用户支付后支付宝会以GET方法请求returnUrl,并且携带out_trade_no,trade_no,total_amount等参数.request.setReturnUrl(aliPayClientConfig.getReturnUrl());AlipayTradePagePayResponse response=null;try{//完成签名并执行请求response=alipayClient.pageExecute(request);if(response.isSuccess()){log.debug("支付宝支付 - 调用成功");return response.getBody();}else{log.error("支付宝支付 - 调用失败");log.error(response.getMsg());return null;}}catch(AlipayApiException e){log.error("支付宝支付 - 创建支付交易失败");throw new ServiceErrorException(ResultCode.ERROR, "支付宝支付 - 创建支付交易失败");}}
3.支付通知
https://opendocs.alipay.com/open/270/105902
/*** 支付成功回调函数* @param params* @return*/@PostMapping("/callback")public String callback(@RequestParam Map<String,String> params){log.debug("收到支付宝回调");try{//验签boolean signVerified = AlipaySignature.rsaCheckV1(params,aliPayClientConfig.getAliPayPublicKey(),AlipayConstants.CHARSET_UTF8,AlipayConstants.SIGN_TYPE_RSA2) ; //调用SDK验证签名//验签成功if(signVerified){log.debug("验签成功");//1.商家需要验证该通知数据中的 out_trade_no 是否为商家系统中创建的订单号String orderNo = params.get("out_trade_no");OrderInfo orderInfo = orderInfoService.getOrderByOrderNo(orderNo);if (orderInfo == null){log.error("订单不存在");return "failure";}//2.判断 total_amount 是否确实为该订单的实际金额(即商家订单创建时的金额)String totalAmount = params.get("total_amount");if (!totalAmount.equals(orderInfo.getTotalFee().toString())){log.error("金额校验失败");return "failure";}//3.校验通知中的 seller_id(或者 seller_email ) 是否为 out_trade_no 这笔单据的对应的操作方String sellerId = params.get("seller_id");if (!aliPayClientConfig.getSellerId().equals(sellerId)){log.error("商家PID校验失败");return "failure";}//4.验证 app_id 是否为该商家本身String appId = params.get("app_id");if (!aliPayClientConfig.getAppId().equals(appId)){log.error("应用APPID校验失败");return "failure";}//5.在支付宝的业务通知中,只有交易通知状态为 TRADE_SUCCESS 或 TRADE_FINISHED 时,// 支付宝才会认定为买家付款成功。String tradeStatus = params.get("trade_status");if (!"TRADE_SUCCESS".equals(tradeStatus)){log.error("支付未成功");return "failure";}//支付成功后 - 处理订单aliPayService.processOrder(params);//除了success外其他返回均认为是失败return "success";}else{log.error("验签失败");return "failure";}}catch(AlipayApiException e){log.error("验签异常");e.printStackTrace();return "failure";}}
4.查询支付
https://opendocs.alipay.com/open/028woa
/*** 查询订单* @param orderNo* @return*/@Overridepublic boolean query(String orderNo) {//请求AlipayTradeQueryRequest request=new AlipayTradeQueryRequest();//数据AlipayTradeQueryModel bizModel=new AlipayTradeQueryModel();bizModel.setOutTradeNo(orderNo);request.setBizModel(bizModel);try{//完成签名并执行请求AlipayTradeQueryResponse response=alipayClient.execute(request);if(response.isSuccess()){log.debug("查询订单{}成功",orderNo);Gson gson = new Gson();HashMap<String,Object> resultMap=gson.fromJson(response.getBody(),HashMap.class);String tradeStatus = (String) resultMap.get("trade_status");if (tradeStatus.equals("TRADE_SUCCESS")){ //订单支付已完成log.info("调用订单查询接口 - 订单已支付完成");return true;}return false;}else{log.error("查询订单{}失败,响应数据是{}.",orderNo,response.getBody());return false;}}catch(AlipayApiException e){log.error("查询订单{}异常",orderNo);return false;}}
5.取消支付
https://opendocs.alipay.com/open/028wob
/*** 支付宝取消订单接口* @param orderNo*/@Overridepublic void closeOrder(String orderNo) {//请求AlipayTradeCloseRequest request=new AlipayTradeCloseRequest();//数据AlipayTradeCloseModel bizModel=new AlipayTradeCloseModel();bizModel.setOutTradeNo(orderNo);request.setBizModel(bizModel);try{//完成签名并执行请求AlipayTradeCloseResponse response=alipayClient.execute(request);if(response.isSuccess()){log.debug("订单:{}取消成功",orderNo);}else{log.debug("订单:{}未创建,因此也可认为本次取消成功.",orderNo);}}catch(AlipayApiException e){log.error("订单{}取消异常",orderNo);throw new ServiceErrorException(ResultCode.ERROR, "订单取消异常");}}
总结
支付回调中可能会存在验签一直失败的问题,出现这个问题的可能是公钥使用出错,验签使用的是支付宝公钥而不是应用公钥,如果开发者在开发过程中,出现验证一直不通过的问题可以尝试检查一下
以上就是就是全部内容,本文仅仅简单介绍了支付宝支付的部分API的使用,还有退款以及账单等相关操作后续使用到了会继续更新。
Java对接第三方支付渠道之支付宝支付相关推荐
- Java对接第三方支付渠道之微信支付APIV3版本
提示:微信支付APIV3版本对接流程梳理,目前微信支付提供APIV3和APIV2两个版本,简而言之,V3版本的安全性比V2更高. Java对接第三方支付渠道之微信支付APIV3版本 一.接入指引 1. ...
- 支付系统实战 | 支付宝支付
文章目录 1.支付 2.支付宝支付 支付分类 快捷支付 手机支付 二维码支付 声波支付 NFC支付 iptv支付 指纹支付 刷脸支付 3.沙箱(沙盒) 4.支付流程 5.支付宝支付准备工作 6.代码开 ...
- 三方支付与微信,支付宝支付有什么优势
西米支付网(www.45ri.com) 首先我们来看一下,财付通 (又称微信支付).支付宝支付 ,三方支付的相同之处与关联 (1)三方支付又称非银行清算机构,是除了银行之外能够合理合法进行收付款服务 ...
- 李洪强iOS开发支付集成之支付宝支付
iOS开发支付集成之支付宝支付 下载支付宝SDK 首先是开发包下载,还是比较难发现的,网上以前文章中的链接都打不开,我找了好久才找到的.最新的地址在这里(注意的是下载出来的SDK包里面并没有传说中的开 ...
- vue 在微信公众号里使用支付宝支付(h5支付宝支付)
vue 在微信公众号里使用支付宝支付(h5支付宝支付) 需求:在微信公众号里面支持支付宝支付. 思路:微信是不能直接调用支付宝的,所以我们需要使用一个中间页提示用户在浏览器中打开,然后进行支付宝网页或 ...
- 支付+电商双系统项目笔记(七)支付系统:支付宝支付开发
目录 一.支付系统介绍 二.代码解析 1.支付宝支付参数配置 2.controller类 3.service类 4.dao类 三.支付演示 一.支付系统介绍 该支付系统实现了支付宝的网站支付功能(微信 ...
- java对接银联商务公众号+服务窗支付(1)
java实现银联商务公众号+服务窗对接----支付下单 GitLab地址:https://gitlab.com/982837387/UnionPayGetWay.git 本文对接银联商务公众号+服务窗 ...
- java对接银联商务公众号+服务窗支付(5)
java实现银联商务公众号+服务窗对接----订单撤销 本文对接银联商务公众号+服务窗支付,实现支付下单.订单查询.订单退款.退款查询和订单关闭几个功能,使用到银联商务的公众+服务窗支付接口规范,请自 ...
- java对接银联商务公众号+服务窗支付(4)
java实现银联商务公众号+服务窗对接----退款查询 本文对接银联商务公众号+服务窗支付,实现支付下单.订单查询.订单退款.退款查询和订单关闭几个功能,使用到银联商务的公众+服务窗支付接口规范,请自 ...
最新文章
- BP网络Python实现代码
- [数据库基础]——索引详解
- tensorflow随笔-滑动平均模型
- Vue项目实战08 : vue之mixin理解与使用
- opengl 纹理贴到对应的位置_一步步学OpenGL(27) -《公告牌技术与几何着色器》
- 分享:一款前端布局工具(alloydesigner)
- MapReduce案例(数据中获取最大值TopN)
- 《高翔视觉slam十四讲》学习笔记 第七讲 视觉里程计
- 074-enable-right-click
- html苹果笔记本文稿如何转换,苹果电脑的pages文档想要变成word格式该如何转换...
- matlab里peaks,MATLAB中peaks函數的用法
- [渝粤教育] 北京化工大学 自然辩证法概论 参考 资料
- Python实现自省的方法有哪些?
- 如何利用一篇高质量软文文案进行网络推广|媒介启航
- S5PV210实验板发布
- Springboot(编程不良人)
- 高脂肪饮食肥胖动物模型 人类肥胖症及其共病特征的动物模型
- R语言绘制美国疫情地图(可交互式)
- carbide.c++ 插件开发入门(转)
- 鼠标光标设置——就是玩儿~