提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档
easy支付官方文档:https://opendocs.alipay.com/open/009ys9
通用版文档:https://opendocs.alipay.com/open/02np94
支付宝沙箱的配置:
注册支付宝开发者账户,进入开发者控制台
沙箱快捷入口:
https://open.alipay.com/develop/sandbox/app
沙箱的界面:
com.alipay.sdk alipay-easysdk 2.2.2
#阿里沙箱支付配置 alipay: #签名算法 signType: #应用ID appId: #应用私钥 appPrivateKey: #支付宝公钥 publicKey: #回调地址 notifyUrl:
/** * @author :Mr.ZJW * @date :Created 2023/9/20 17:40 * @description:alipay沙箱环境配置 */ @Slf4j @Data @Component @ConfigurationProperties(prefix = "alipay") public class AlipayConfig { /** * appId */ private String appId; /** * 私钥 */ private String appPrivateKey; /** * 公钥 */ private String publicKey; /** * 回调地址 */ private String notifyUrl; /** * 支付宝配置初始化,公钥模式 */ @PostConstruct public void init() { Config config = new Config(); //#基础配置 config.protocol = "https"; //协议 config.gatewayHost = "openapi.alipaydev.com"; //支付宝网关 config.signType = "RSA2"; //签名方式 //#业务配置 config.appId = this.appId; //应用id config.merchantPrivateKey = this.appPrivateKey; 应用私钥 config.alipayPublicKey = this.publicKey; //支付宝公钥 config.notifyUrl = this.notifyUrl; //回调地址 Factory.setOptions(config); log.info("支付宝配置初始化完成"); } }
import com.alipay.easysdk.factory.Factory; import com.alipay.easysdk.payment.page.models.AlipayTradePagePayResponse; import com.google.common.collect.Maps; import com.jowell.common.exception.base.BaseException; import com.jowell.common.response.Result; import lombok.extern.slf4j.Slf4j; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.ResponseBody; import javax.servlet.http.HttpServletRequest; import java.util.Map; /** * @author :Mr.ZJW * @date :Created 2023/9/20 17:53 * @description:支付controller */ @Slf4j @RequestMapping("/alipay") @Controller @ResponseBody public class TestAlipayController { /** * 支付接口 * * @param subject 名称 * @param outTradeNo 订单号 * @param totalAmount 金额 * @return / */ @GetMapping("/pay") public String pay(String subject, String outTradeNo, String totalAmount) { AlipayTradePagePayResponse response; try { response = Factory.Payment.Page().pay(subject, outTradeNo, totalAmount, ""); } catch (Exception e) { log.error("支付宝付款调用失败,原因:" + e.getMessage()); throw new BaseException("网络异常,请刷新后重试"); } return response.getBody(); }
接口测试:
访问URL进行测试,测试的url格式:http://localhost:10000/alipay/pay?subject=支付测试&outTradeNo=D239211000000&totalAmount=1
效果:
进行用买家账号密码登录:
输入支付密码进行支付:
支付成功:
回调接口要有一个外网域名,这里可以使用花生壳以及我分享过的一遍文章:
文章链接:https://blog.csdn.net/javaeEEse/article/details/117983797?spm=1001.2014.3001.5502
把这个域名复制到配置文件里的回调地址上。
回调完整代码:
/** * 支付宝回调 */ @PostMapping("/notify") public Resultnotify(HttpServletRequest request) { log.info("支付宝回调成功"); //校验是否成功 if ("TRADE_SUCCESS".equals(request.getParameter("trade_status"))) { //#解析回调数据 Map params = Maps.newHashMap(); Map requestParams = request.getParameterMap(); for (String name : requestParams.keySet()) { params.put(name, request.getParameter(name)); } //订单号 String tradeNo = params.get("out_trade_no"); //支付金额 String gmtPayment = params.get("gmt_payment"); //支付宝交易凭证号 String alipayTradeNo = params.get("trade_no"); //#支付宝验签,防止不法分子伪造请求 try { Boolean flag = Factory.Payment.Common().verifyNotify(params); if (Boolean.TRUE.equals(flag)) { log.info("交易名称: " + params.get("subject")); log.info("交易状态: " + params.get("trade_status")); log.info("支付宝交易凭证号: " + params.get("trade_no")); log.info("商户订单号: " + params.get("out_trade_no")); log.info("交易金额: " + params.get("total_amount")); log.info("买家在支付宝唯一id: " + params.get("buyer_id")); log.info("买家付款时间: " + params.get("gmt_payment")); log.info("买家付款金额: " + params.get("buyer_pay_amount")); } else { log.error("异步通知验签失败"); return Result.error("fail"); } } catch (Exception e) { log.error("异步发生异常{}", e.getMessage()); return Result.error("fail"); } //#进行一些业务逻辑,如更新订单等操作 } return Result.success(); }