支付宝支付成功返回结果封装
import com.alibaba.fastjson.annotation.JSONField;
import java.math.BigDecimal;
import java.util.Date;
/**
* APP支付返回业务参数
* @date 2018年1月24日
*/
public class AlipayAppPayRet{
// 通知时间
@JSONField(format="yyyy-MM-dd HH:mm:ss")
private Date notify_time;
// 通知类型
private String notify_type;
// 通知校验ID
private String notify_id;
// 编码格式
private String charset;
// 接口版本
private String version;
// 签名类型
private String sign_type;
// 签名
private String sign;
// 授权方的app_id
private String auth_app_id;
// 支付宝交易号
private String trade_no;
// 开发者的app_id
private String app_id;
// 商户订单号
private String out_trade_no;
// 商户业务号
private String out_biz_no;
// 买家支付宝用户号
private String buyer_id;
// 卖家支付宝用户号
private String seller_id;
// 交易状态
private String trade_status;
// 订单金额
private BigDecimal total_amount;
// 实收金额
private BigDecimal receipt_amount;
// 开票金额
private BigDecimal invoice_amount;
// 付款金额
private BigDecimal buyer_pay_amount;
// 集分宝金额
private BigDecimal point_amount;
// 总退款金额
private BigDecimal refund_fee;
// 订单标题
private String subject;
// 商品描述
private String body;
// 交易创建时间
@JSONField(format="yyyy-MM-dd HH:mm:ss")
private Date gmt_create;
// 交易付款时间
@JSONField(format="yyyy-MM-dd HH:mm:ss")
private Date gmt_payment;
// 交易退款时间
@JSONField(format="yyyy-MM-dd HH:mm:ss")
private Date gmt_refund;
// 交易结束时间
@JSONField(format="yyyy-MM-dd HH:mm:ss")
private Date gmt_close;
// 支付金额信息
private String fund_bill_list;
// 优惠券信息
private String voucher_detail_list;
/**
* 公共回传参数,如果请求时传递了该参数,则返回给商户时会在异步通知时将该参数原样返回。 本参数必须进行UrlEncode之后才可以发送给支付宝
*/
private String passback_params;
public String getTrade_no() {
return trade_no;
}
public void setTrade_no(String trade_no) {
this.trade_no = trade_no;
}
public String getApp_id() {
return app_id;
}
public void setApp_id(String app_id) {
this.app_id = app_id;
}
public String getOut_trade_no() {
return out_trade_no;
}
public void setOut_trade_no(String out_trade_no) {
this.out_trade_no = out_trade_no;
}
public String getOut_biz_no() {
return out_biz_no;
}
public void setOut_biz_no(String out_biz_no) {
this.out_biz_no = out_biz_no;
}
public String getBuyer_id() {
return buyer_id;
}
public void setBuyer_id(String buyer_id) {
this.buyer_id = buyer_id;
}
public String getSeller_id() {
return seller_id;
}
public void setSeller_id(String seller_id) {
this.seller_id = seller_id;
}
public String getTrade_status() {
return trade_status;
}
public void setTrade_status(String trade_status) {
this.trade_status = trade_status;
}
public BigDecimal getTotal_amount() {
return total_amount;
}
public void setTotal_amount(BigDecimal total_amount) {
this.total_amount = total_amount;
}
public BigDecimal getReceipt_amount() {
return receipt_amount;
}
public void setReceipt_amount(BigDecimal receipt_amount) {
this.receipt_amount = receipt_amount;
}
public BigDecimal getInvoice_amount() {
return invoice_amount;
}
public void setInvoice_amount(BigDecimal invoice_amount) {
this.invoice_amount = invoice_amount;
}
public BigDecimal getBuyer_pay_amount() {
return buyer_pay_amount;
}
public void setBuyer_pay_amount(BigDecimal buyer_pay_amount) {
this.buyer_pay_amount = buyer_pay_amount;
}
public BigDecimal getPoint_amount() {
return point_amount;
}
public void setPoint_amount(BigDecimal point_amount) {
this.point_amount = point_amount;
}
public BigDecimal getRefund_fee() {
return refund_fee;
}
public void setRefund_fee(BigDecimal refund_fee) {
this.refund_fee = refund_fee;
}
public String getSubject() {
return subject;
}
public void setSubject(String subject) {
this.subject = subject;
}
public String getBody() {
return body;
}
public void setBody(String body) {
this.body = body;
}
public Date getGmt_create() {
return gmt_create;
}
public void setGmt_create(Date gmt_create) {
this.gmt_create = gmt_create;
}
public Date getGmt_payment() {
return gmt_payment;
}
public void setGmt_payment(Date gmt_payment) {
this.gmt_payment = gmt_payment;
}
public Date getGmt_refund() {
return gmt_refund;
}
public void setGmt_refund(Date gmt_refund) {
this.gmt_refund = gmt_refund;
}
public Date getGmt_close() {
return gmt_close;
}
public void setGmt_close(Date gmt_close) {
this.gmt_close = gmt_close;
}
public String getFund_bill_list() {
return fund_bill_list;
}
public void setFund_bill_list(String fund_bill_list) {
this.fund_bill_list = fund_bill_list;
}
public String getVoucher_detail_list() {
return voucher_detail_list;
}
public void setVoucher_detail_list(String voucher_detail_list) {
this.voucher_detail_list = voucher_detail_list;
}
public String getPassback_params() {
return passback_params;
}
public void setPassback_params(String passback_params) {
this.passback_params = passback_params;
}
public Date getNotify_time() {
return notify_time;
}
public void setNotify_time(Date notify_time) {
this.notify_time = notify_time;
}
public String getNotify_type() {
return notify_type;
}
public void setNotify_type(String notify_type) {
this.notify_type = notify_type;
}
public String getNotify_id() {
return notify_id;
}
public void setNotify_id(String notify_id) {
this.notify_id = notify_id;
}
public String getCharset() {
return charset;
}
public void setCharset(String charset) {
this.charset = charset;
}
public String getVersion() {
return version;
}
public void setVersion(String version) {
this.version = version;
}
public String getSign_type() {
return sign_type;
}
public void setSign_type(String sign_type) {
this.sign_type = sign_type;
}
public String getSign() {
return sign;
}
public void setSign(String sign) {
this.sign = sign;
}
public String getAuth_app_id() {
return auth_app_id;
}
public void setAuth_app_id(String auth_app_id) {
this.auth_app_id = auth_app_id;
}
}
下单和回调接口
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONException;
import com.alipay.api.AlipayApiException;
import com.alipay.api.AlipayClient;
import com.alipay.api.AlipayConstants;
import com.alipay.api.DefaultAlipayClient;
import com.alipay.api.domain.AlipayTradeAppPayModel;
import com.alipay.api.internal.util.AlipaySignature;
import com.alipay.api.request.AlipayTradeAppPayRequest;
import com.alipay.api.response.AlipayTradeAppPayResponse;
import plugins.pay.alipay.domain.AlipayAppPayRet;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
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.RestController;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.math.BigDecimal;
import java.text.DecimalFormat;
import java.util.*;
@RestController
@Api(tags="支付接口")
@RequestMapping("/Indent")
public class H5IndentController {
@GetMapping("/addAli")
@ApiOperation(value = "支付宝新增订单", notes = "支付宝新增订单")
public Map<String,Object> addWechat(HttpServletRequest request, HttpServletResponse response){
//支付宝价格为元,需要先处理价格(1800的单位是分)
BigDecimal decimal = getBigDecimal(1800);
//开始生成支付宝预支付
String orderString; //返回给app的字符串
//创建支付宝APP支付的数据模型
//注:此处用的支付宝官方的SDK,所以使用工具类填写必填参数
try {
AlipayTradeAppPayModel model = getAppPayModel("天天乐", "会员充值",
"商户订单id", 30, decimal);
//支付统一下单
orderString = preOrder4App(model, "video");
// TODO 保存数据
// 返回结果
HashMap<String, Object> map = new HashMap<>();
map.put("orderString", orderString);
map.put("indentId", "商户订单id");
return map;
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
// 支付宝收款回调
@PostMapping("/aliNotify")
public String aliNotify(HttpServletRequest request){
//解析回调请求并验签
try {
AlipayAppPayRet ret = parseRequest(request, false);
String tradeStatus = ret.getTrade_status();
if(tradeStatus.equals("TRADE_SUCCESS")){
// TODO 开始进行订单处理,自行完善
String result = updateIndent(ret.getOut_trade_no());
System.out.println("----------------------------------------------------------------------交易完成!");
return result;
}else{
System.out.println("支付状态错误,交易状态:" + tradeStatus);
}
} catch (Exception e) {
e.printStackTrace();
}
//应答支付宝
return "success";
}
// 解析支付宝APP支付回调并验签
public static AlipayAppPayRet parseRequest(HttpServletRequest request, boolean enc) throws Exception {
return (AlipayAppPayRet) convertMap2Bean(getParamsMap(request.getParameterMap(), enc), AlipayAppPayRet.class);
}
// 将Map转换成对象
public static Object convertMap2Bean(Map<String, String> map, Class<?> clazz) throws Exception {
Map<String, Object> objMap = new TreeMap<>();
//预处理map,将里面的json字符串字段转换成对象
Set<String> keys = map.keySet();
for (String key : keys) {
String str = map.get(key);
try {
//如果是JSON字符串,则转换成对象,再添加到objMap中
objMap.put(key, JSON.parse(str));
} catch (JSONException e) {
//如果不是JSON字符串,则直接添加到objMap中
objMap.put(key, str);
} catch (Exception e) {
//其余错误抛出
e.printStackTrace();
}
}
Object obj = JSON.parseObject(JSON.toJSONString(objMap), clazz);
return obj;
}
// 验签并返回参数
@SuppressWarnings("rawtypes")
public static Map<String, String> getParamsMap(Map requestParamterMap, boolean enc) throws Exception {
Map<String, String> params = new HashMap<>();
for (Iterator iter = requestParamterMap.keySet().iterator(); iter.hasNext(); ) {
String name = (String) iter.next();
String[] values = (String[]) requestParamterMap.get(name);
String valueStr = "";
for (int i = 0; i < values.length; i++) {
valueStr = (i == values.length - 1) ? valueStr + values[i] : valueStr + values[i] + ",";
}
if (enc) {
valueStr = new String(valueStr.getBytes("ISO-8859-1"), "utf-8");
}
params.put(name, valueStr);
}
// 切记alipaypublickey是支付宝的公钥,请去open.alipay.com对应应用下查看。
// boolean AlipaySignature.rsaCheckV1(Map<String, String> params, String
// publicKey, String charset, String sign_type)
boolean flag = AlipaySignature.rsaCheckV1(params, "支付宝公钥", AlipayConstants.CHARSET_UTF8, "RSA2");
if (!flag) {
throw new RuntimeException("验签失败");
}
return params;
}
// 支付宝生成APP订单
public static String preOrder4App(AlipayTradeAppPayModel model, String suffix) throws Exception {
// 实例化客户端
AlipayClient alipayClient = new DefaultAlipayClient(
// 支付地址
"https://openapi.alipay.com/gateway.do",
// 应用id
"商户APPID",
// 私钥
"商户私钥",
// 固定值json,参数类型,
"json",
// 编码方式
"UTF-8",
// 公钥
"支付宝公钥",
// 签名加密方式
"RSA2");
// 实例化具体API对应的request类,类名称和接口名称对应,当前调用接口名称:alipay.trade.app.pay
AlipayTradeAppPayRequest request = new AlipayTradeAppPayRequest();
request.setBizModel(model);
if (suffix == null || "".equals(suffix)) {
throw new RuntimeException("回调地址后缀不能为空");
}
request.setNotifyUrl("商户后台接口地址");
try {
// 这里和普通的接口调用不同,使用的是sdkExecute
AlipayTradeAppPayResponse response = alipayClient.sdkExecute(request);
return response.getBody();
} catch (AlipayApiException e) {
e.printStackTrace();
throw e;
}
}
// 处理金额
public static BigDecimal getBigDecimal(int a){
double b = a;
b = b / 100;
DecimalFormat df = new DecimalFormat("#.00");
String s = df.format(b);
BigDecimal f = new BigDecimal(s);
return f;
}
/**
* 设置必要的业务参数
* @param body 商品描述
* @param subject 商品的标题/交易标题/订单标题/订单关键字等
* @param out_trade_no 商户订单号
* @param timeout_express 有效时间,单位为分钟
* @param total_account 价格,传入带两位小数的数字 字符串,测试环境时为固定值0.01
* @return
* @throws Exception
*/
public static AlipayTradeAppPayModel getAppPayModel(String body, String subject, String out_trade_no,
int timeout_express, BigDecimal total_account) throws Exception {
// SDK已经封装掉了公共参数,这里只需要传入业务参数。以下方法为sdk的model入参方式(model和biz_content同时存在的情况下取biz_content)。
AlipayTradeAppPayModel model = new AlipayTradeAppPayModel();
model.setBody(body);
model.setSubject(subject);
model.setOutTradeNo(out_trade_no);
model.setTimeoutExpress(timeout_express+"m");
model.setTotalAmount(total_account.toString());
model.setProductCode("QUICK_MSECURITY_PAY");
return model;
}
}
完成