支付宝支付手机浏览器H5支付

编程

本文开发环境:IDEA + Tomcat8.5 + 支付宝沙箱环境

补充:调用沙箱环境接口,需要安装沙箱环境下的支付宝APP,不了解的小伙伴可以参考上方 支付宝支付—沙箱环境使用。

下载运行测试Demo

官方Demo下载链接:手机网站支付

下载后导入 IDEA 中后需要调整的参数如下:

AlipayConfig.java

public class AlipayConfig {

// 商户appid

public static String APPID = "2016101700705301";

// 私钥 pkcs8格式的

public static String RSA_PRIVATE_KEY = "";

// 服务器异步通知页面路径 需http://或者https://格式的完整路径,不能加?id=123这类自定义参数,必须外网可以正常访问

public static String notify_url = "http://ngrok.sscai.club/alipay_trade_wap_pay_java_utf_8_war_exploded/notify_url.jsp";

// 页面跳转同步通知页面路径 需http://或者https://格式的完整路径,不能加?id=123这类自定义参数,必须外网可以正常访问 商户可以自定义同步跳转地址

public static String return_url = "http://ngrok.sscai.club/alipay_trade_wap_pay_java_utf_8_war_exploded/return_url.jsp";

// 请求网关地址

public static String URL = "https://openapi.alipaydev.com/gateway.do";

// 编码

public static String CHARSET = "UTF-8";

// 返回格式

public static String FORMAT = "json";

// 支付宝公钥

public static String ALIPAY_PUBLIC_KEY = "";

// 日志记录目录

public static String log_path = "/log";

// RSA2

public static String SIGNTYPE = "RSA2";

}

几个主要的参数:

  1. APPID :商户appid
  2. RSA_PRIVATE_KEY:应用私钥
  3. ALIPAY_PUBLIC_KEY:支付宝公钥「注意不是应用公钥」

这几个参数不清楚的,可以看一下 沙箱环境使用,或者看一下官方文档参数说明。

项目启动后如下图所示:

Maven项目中的使用

Maven中的使用其实跟上篇 支付宝支付-支付宝PC端扫码支付 代码非常的像,换汤不换药,改几个参数,具体如下:

pom.xml中引入支付宝SDK依赖

<dependency>

<groupId>com.alipay.sdk</groupId>

<artifactId>alipay-sdk-java</artifactId>

<version>3.1.0</version>

</dependency>

配置可以单独创建一个类,静态初始化参数:

public class AlipayConfig {

// [沙箱环境]应用ID,您的APPID,收款账号既是您的APPID对应支付宝账号

public static String app_id = "";

// [沙箱环境]商户私钥,您的PKCS8格式RSA2私钥

public static String merchant_private_key = "";

// [沙箱环境]支付宝公钥,查看地址:https://openhome.alipay.com/platform/keyManage.htm 对应APPID下的支付宝公钥。

public static String alipay_public_key = "";

// [沙箱环境]服务器异步通知页面路径 需http://格式的完整路径,不能加?id=123这类自定义参数,必须外网可以正常访问

public static String notify_url = "http://ngrok.sscai.club/alipay/aliPayNotify_url";

// [沙箱环境]页面跳转同步通知页面路径 需http://格式的完整路径,不能加?id=123这类自定义参数,必须外网可以正常访问

public static String return_url = "http://ngrok.sscai.club/index.html#/alipay/success";

// [沙箱环境]

public static String gatewayUrl = "https://openapi.alipaydev.com/gateway.do";

}

至于接口啥的基本就是可以参考上方运行的Demo了。

简单看看生成支付宝订单接口「没有使用开源SDK」。

@Transactional

public String alipayOrder(AlipayOrderRequest alipayOrderRequest) throws AlipayApiException {

//获得初始化的AlipayClient

AlipayClient alipayClient = new DefaultAlipayClient(AlipayConfig.gatewayUrl,

AlipayConfig.app_id,

AlipayConfig.merchant_private_key,

"json",

AlipayConfig.charset,

AlipayConfig.alipay_public_key,

AlipayConfig.sign_type);

//设置请求参数

String payType = alipayOrderRequest.getPayType();

// wap

AlipayTradeWapPayRequest alipayWapRequest = new AlipayTradeWapPayRequest();

alipayWapRequest.setReturnUrl(AlipayConfig.return_url);

alipayWapRequest.setNotifyUrl(AlipayConfig.notify_url);

//商户订单号,商户网站订单系统中唯一订单号,必填

String out_trade_no = alipayOrderRequest.getWidOutTradeNo();

//付款金额,必填

String total_amount = alipayOrderRequest.getWidTotalFee();

//订单名称,必填

String subject = alipayOrderRequest.getWidSubject();

//商品描述,可空

String body = alipayOrderRequest.getWIDbody();

//拼接参数

alipayWapRequest.setBizContent("{"out_trade_no":""+ out_trade_no +"","

+ ""total_amount":""+ total_amount +"","

+ ""subject":""+ subject +"","

+ ""body":""+ body +"","

+ ""product_code":"FAST_INSTANT_TRADE_PAY"}");

// 发起请求

return alipayClient.pageExecute( alipayWapRequest).getBody();

}

手机网站支付接口调用后返回的是一个 Form 表单,也就是 result 实际是一段 Html 代码,然后把 result 传给前段调用即可,下面是返回的 Form 的一个示例:

  <form name="punchout_form" method="post" action="https://openapi.alipaydev.com/gateway.do?charset=UTF-8&method=alipay.trade.wap.pay&sign=xx&return_url=http%3A%2F%2Fngrok.sscai.club%2Falipay_trade_wap_pay_java_utf_8_war_exploded%2Freturn_url.jsp&notify_url=http%3A%2F%2Fngrok.sscai.club%2Falipay_trade_wap_pay_java_utf_8_war_exploded%2Fnotify_url.jsp&version=1.0&app_id=2016101700705301&sign_type=RSA2&timestamp=2020-01-08+14%3A09%3A58&alipay_sdk=alipay-sdk-java-3.3.0&format=json"> 

<input type="hidden" name="biz_content" value="{&quot;body&quot;:&quot;购买测试商品0.01元&quot;,&quot;out_trade_no&quot;:&quot;20201814955421&quot;,&quot;product_code&quot;:&quot;QUICK_WAP_WAY&quot;,&quot;subject&quot;:&quot;手机网站支付测试商品&quot;,&quot;timeout_express&quot;:&quot;2m&quot;,&quot;total_amount&quot;:&quot;0.01&quot;}" />

<input type="submit" value="立即支付" style="display:none" />

</form>

怎么调用呢?下面是一段我在vue中的测试代码片段,前段接收到后端返回的 Form 表单进行提交:

const div = document.createElement("div");

console.log("我是后端返回的数据:"+res.result)

div.innerHTML = res.result;

document.body.appendChild(div);

console.log("punchout_form:"+document.forms.punchout_form)

document.forms.punchout_form.submit();

支付成功后会自动重定向到配置的跳转界面,由后端的的 return_url 参数控制。

再看看支付成功后的回调接口「没有使用开源的SDK演示」:

public String alipaynotify(Model model, HttpServletRequest request) {

log.info("支付宝异步回调 ------------beg-----------");

String result = "fail";

//获取支付宝POST过来反馈信息

/* *

* 功能:支付宝服务器异步通知页面

* 说明:

* 以下代码只是为了方便商户测试而提供的样例代码,商户可以根据自己网站的需要,按照技术文档编写,并非一定要使用该代码。

* 该代码仅供学习和研究支付宝接口使用,只是提供一个参考。

*/

Map<String, String> params=this.getAlipayRequest(request);

if(params == null || params.size()==0){

BufferedReader bufferReader = null;

StringBuilder sb = new StringBuilder();

try {

bufferReader = new BufferedReader(request.getReader());

String line = null;

while ((line = bufferReader.readLine()) != null) {

sb.append(new String(line.getBytes("ISO-8859-1"), "utf-8"));

}

} catch (IOException e) {

e.printStackTrace();

}

String body= null;

try {

body = URLDecoder.decode(sb.toString(),"UTF-8");

} catch (UnsupportedEncodingException e) {

e.printStackTrace();

}

params=UriComponentsBuilder.newInstance().query(body).build().getQueryParams().toSingleValueMap();

}

boolean signVerified =false;

try {

signVerified = AlipaySignature.rsaCheckV1(params, AlipayConfig.alipay_public_key, AlipayConfig.charset, AlipayConfig.sign_type);

} catch (AlipayApiException e1) {

// TODO Auto-generated catch block

log.error("由于"+e1.getErrMsg()+"返回给支付宝系统的结果result:fail");

model.addAttribute("result", "fail");

return result;

} //调用SDK验证签名

//——请在这里编写您的程序(以下代码仅作参考)——

/* 实际验证过程建议商户务必添加以下校验:

1、需要验证该通知数据中的out_trade_no是否为商户系统中创建的订单号,

2、判断total_amount是否确实为该订单的实际金额(即商户订单创建时的金额),

3、校验通知中的seller_id(或者seller_email) 是否为out_trade_no这笔单据的对应的操作方(有的时候,一个商户可能有多个seller_id/seller_email)

4、验证app_id是否为该商户本身。

*/

log.error("支付宝验证签名:---------------------------------"+signVerified);

if(signVerified) {//验证成功

//商户订单号

//交易状态

log.info("支付宝异步回调验签成功!");

String trade_status = params.get("trade_status");

if("TRADE_FINISHED".equals(trade_status)){

//判断该笔订单是否在商户网站中已经做过处理

//如果没有做过处理,根据订单号(out_trade_no)在商户网站的订单系统中查到该笔订单的详细,并执行商户的业务程序

//如果有做过处理,不执行商户的业务程序

//注意:

//退款日期超过可退款期限后(如三个月可退款),支付宝系统发送该交易状态通知

try {

// 在这里处理支付成功后的操作,比如修改订单状态等等

coding...

result = "success";

} catch (Exception e) {

log.error(e.getMessage());

result = "fail";

}

}else if ("TRADE_SUCCESS".equals(trade_status)){

//判断该笔订单是否在商户网站中已经做过处理

//如果没有做过处理,根据订单号(out_trade_no)在商户网站的订单系统中查到该笔订单的详细,并执行商户的业务程序

//如果有做过处理,不执行商户的业务程序

//注意:

//付款完成后,支付宝系统发送该交易状态通知

try {

// 在这里处理支付成功后的操作,比如修改订单状态等等

coding...

result = "success";

} catch (Exception e) {

log.error(e.getMessage());

result = "fail";

}

}else{

result = "fail";

}

}else {//验证失败

result = "fail";

//调试用,写文本函数记录程序运行情况是否正常

//String sWord = AlipaySignature.getSignCheckContentV1(params);

//AlipayConfig.logResult(sWord);

log.debug("支付宝异步回调验签失败");

}

log.debug("异步回调返回给支付宝系统的结果result:"+result);

model.addAttribute("result", result);

log.info("支付宝异步回调 -------------end ------------");

return result;

}

该方法返回给支付宝的 result 就 success、fail 两个结果。

从以上看来,其实不难发现支付宝支付是非常简单的,尽管我上边贴了大量的代码,其实采用开源SDK的话可以更加缩减、美化一些,如下是支付成功的截图。

ok,这篇文章就到这结束了,上边并没有详细介绍接口调用、参数说明等,详细介绍请查看官方文档:https://docs.open.alipay.com/60/104790/

本文源码下载

可运行的官方手机网站支付Demo:https://www.lanzous.com/i8oe2sb

文章最后

博客地址:https://www.cgblog.com/niceyoo

如果觉得这篇文章有丶东西,不妨关注一下我,关注是对我最大的鼓励~

18年专科毕业后,期间一度迷茫,最近我创建了一个公众号用来记录自己的成长。

以上是 支付宝支付手机浏览器H5支付 的全部内容, 来源链接: utcz.com/z/516093.html

回到顶部