1.蚂蚁金服文档地址
文档入口:https://opendocs.alipay.com/open/270
沙箱文档入口:https://opendocs.alipay.com/open/200/105311
2.支付流程

2.1 首页开发服务中找到沙箱

2.2 页面中找到进入沙箱环境

2.3 生成RSA密钥
进入沙箱应用之后可以看到信息配置部分需要设置RSA2(SHA256)密钥,因为文档很详细了,我就不写了
具体步骤: https://opendocs.alipay.com/open/291/105971
3.支付功能移植到项目
官方Demo:https://opendocs.alipay.com/open/270/106291
官方Demo是使用jsp处理和响应请求的,有兴趣自己下载下来测试下,我这直接整合到Springboot里用Controller处理了
①加入支付功能相关依赖
参考文档:https://docs.open.alipay.com/54/103419
1 2 3 4 5
| <dependency> <groupId>com.alipay.sdk</groupId> <artifactId>alipay-sdk-java</artifactId> <version>3.3.49.ALL</version> </dependency>
|
②加入AlipayConfig
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32
| public static String app_id = "2016080400166558";
public static String merchant_private_key = "====填写自己的====";
public static String alipay_public_key = "====填写自己的====";
public static String notify_url = "http://aatczu.natappfree.cc/alipay.trade.page.pay-JAVA-UTF-8/notify_url.jsp";
public static String return_url = "http://aatczu.natappfree.cc/alipay.trade.page.pay-JAVA-UTF-8/return_url.jsp";
public static String sign_type = "RSA2";
public static String charset = "utf-8";
public static String gatewayUrl = "https://openapi.alipaydev.com/gateway.do";
|
③创建PayController
所在工程:distribution-crowd-7-webui
全类名:com.zzxx.crowd.controller.PayController
1 2 3 4
| @Controller public class PayController {
}
|
④处理付款请求的方法
所在类:com.zzxx.crowd.controller.PayController
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39
| @ResponseBody @RequestMapping(value="/pay", produces="text/html") public String pay(HttpServletRequest request) throws Exception { AlipayClient alipayClient = new DefaultAlipayClient(AlipayConfig.gatewayUrl, AlipayConfig.app_id, AlipayConfig.merchant_private_key, "json", AlipayConfig.charset, AlipayConfig.alipay_public_key, AlipayConfig.sign_type); AlipayTradePagePayRequest alipayRequest = new AlipayTradePagePayRequest(); alipayRequest.setReturnUrl(AlipayConfig.return_url); alipayRequest.setNotifyUrl(AlipayConfig.notify_url); String out_trade_no = new String(request.getParameter("WIDout_trade_no").getBytes("ISO-8859-1"),"UTF-8"); String total_amount = new String(request.getParameter("WIDtotal_amount").getBytes("ISO-8859-1"),"UTF-8"); String subject = new String(request.getParameter("WIDsubject").getBytes("ISO-8859-1"),"UTF-8"); String body = new String(request.getParameter("WIDbody").getBytes("ISO-8859-1"),"UTF-8"); alipayRequest.setBizContent("{\"out_trade_no\":\""+ out_trade_no +"\"," + "\"total_amount\":\""+ total_amount +"\"," + "\"subject\":\""+ subject +"\"," + "\"body\":\""+ body +"\"," + "\"product_code\":\"FAST_INSTANT_TRADE_PAY\"}"); return alipayClient.pageExecute(alipayRequest).getBody(); }
|
⑤return方法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39
| @ResponseBody @RequestMapping("/pay/return") public String payReturn(HttpServletRequest request) throws Exception {
Map<String, String> params = new HashMap<String, String>(); Map<String, String[]> requestParams = request.getParameterMap(); for (Iterator<String> iter = requestParams.keySet().iterator(); iter.hasNext();) { String name = (String) iter.next(); String[] values = (String[]) requestParams.get(name); String valueStr = ""; for (int i = 0; i < values.length; i++) { valueStr = (i == values.length - 1) ? valueStr + values[i] : valueStr + values[i] + ","; } valueStr = new String(valueStr.getBytes("ISO-8859-1"), "utf-8"); params.put(name, valueStr); }
boolean signVerified = AlipaySignature.rsaCheckV1(params, AlipayConfig.alipay_public_key, AlipayConfig.charset, AlipayConfig.sign_type);
if (signVerified) { String out_trade_no = new String(request.getParameter("out_trade_no").getBytes("ISO-8859-1"), "UTF-8");
String trade_no = new String(request.getParameter("trade_no").getBytes("ISO-8859-1"), "UTF-8");
String total_amount = new String(request.getParameter("total_amount").getBytes("ISO-8859-1"), "UTF-8");
return "trade_no:" + trade_no + "<br/>out_trade_no:" + out_trade_no + "<br/>total_amount:" + total_amount; } else { return "验签失败"; }
}
|
⑥notify方法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70
| @ResponseBody @RequestMapping("/pay/notify") public String payNotify(HttpServletRequest request) throws Exception {
Map<String, String> params = new HashMap<String, String>(); Map<String, String[]> requestParams = request.getParameterMap(); for (Iterator<String> iter = requestParams.keySet().iterator(); iter.hasNext();) { String name = (String) iter.next(); String[] values = (String[]) requestParams.get(name); String valueStr = ""; for (int i = 0; i < values.length; i++) { valueStr = (i == values.length - 1) ? valueStr + values[i] : valueStr + values[i] + ","; } valueStr = new String(valueStr.getBytes("ISO-8859-1"), "utf-8"); params.put(name, valueStr); }
boolean signVerified = AlipaySignature.rsaCheckV1(params, AlipayConfig.alipay_public_key, AlipayConfig.charset, AlipayConfig.sign_type);
if (signVerified) {
String trade_status = new String(request.getParameter("trade_status").getBytes("ISO-8859-1"), "UTF-8");
if (trade_status.equals("TRADE_FINISHED")) {
} else if (trade_status.equals("TRADE_SUCCESS")) {
}
return "success";
} else {
return "fail";
}
}
|
⑦将AliPayConfig中的属性配置转移到yml文件
[1]@Value注解不能修饰静态资源
加载类比IOC容器初始化要早,静态资源初始化时IOC容器还没有初始化好,@Value注解的值设置不进去。
[2]解决办法
实现接口org.springframework.beans.factory.InitializingBean
1 2 3 4 5 6 7 8 9 10 11
| @Configuration public class AlipayConfig implements InitializingBean { @Value("${alipay.app_id}") private String appId; @Override public void afterPropertiesSet() throws Exception { app_id = this.appId; }
|