Java对接支付宝支付

本文详细介绍了支付宝支付的业务流程和技术实现,包括预支付订单创建、签名验证、回调通知等核心步骤,并分享了iOS客户端调试过程中遇到的问题及解决办法。

一、参考官方文档:https://docs.open.alipay.com/204/105301/

二、业务流程:

    1.app请求;

    2.校验必传参数;

    3.创建预支付订单;

     4.支付宝签名;

    5.将支付宝签名字符串传递给app

三、业务代码:

    1.支付宝业务逻辑:

package com.yqs.pay.thridpay;

import java.util.Map;

import org.apache.log4j.Logger;

import com.alibaba.fastjson.JSONObject;
import com.dev.util.message.Msg;
import com.pay.service.Pay;
import com.yqs.pay.deal.server.PayServer;
import com.yqs.pay.entity.dim.PayStatus;
import com.yqs.pay.util.ThirdNotifyCheck;
import com.yqs.pay.util.alipay.AlipayUtil;

public class Alipay  implements  ThridPay{
	
	private static Logger log = Logger.getLogger(Alipay.class);

	public Msg<Object> doAdvanceOrder(Pay pay) throws Exception {
		String billCode = pay.getPars().get("billCode");
//		Double  amt=pay.getAmount()*100;
		Double  amt=0.01;//支付宝支付金额是元
		
		String alipayResponse = pay.getTerminal()==3?AlipayUtil.alipayQrCodePay(billCode, String.valueOf(amt)):AlipayUtil.alipayOrderPay("支付宝支付",billCode,String.valueOf(amt));
		if(alipayResponse!=null &&alipayResponse.trim().length()!=0){
			Msg<Object> msg = PayServer.preRecharge(pay,billCode);//维护订单(创建未支付记录和订单)
			if(!msg.status)
				return msg;
			if(pay.getTerminal()==3){
				Msg<Object> msg2 = new Msg<Object>(true,billCode);
				msg2.setData(alipayResponse);
				return msg2;
			}
			return msgFactory.success("支付宝预订单成功!",alipayResponse);
		}
		return msgFactory.fail("支付宝预订单失败!");
	}

	public Msg<Object> callBackNotify(Map<String, String> map) throws Exception {
		String out_trade_no = map.get("out_trade_no");
		int rechargeStatus = map.get("trade_status").equals("TRADE_SUCCESS") ? PayStatus.SUCCESS : PayStatus.FAIL;
		ThirdNotifyCheck.putNotifyOrderID(out_trade_no, System.currentTimeMillis() + ";" + rechargeStatus);
		Msg<Object> msg=PayServer.rechargeNotify(out_trade_no,rechargeStatus);
		if (msg==null || !msg.status){
			log.fatal("支付宝支付成功,回调异常"+JSONObject.toJSONString(msg));
			return msgFactory.fail("支付宝支付回调处理失败");
		}
		return msgFactory.success("支付宝支付回调处理成功");
	}
	

}

2.支付宝工具类:

package com.yqs.pay.util.alipay;

import java.util.HashMap;
import java.util.Map;
import org.apache.log4j.Logger;
import com.alibaba.fastjson.JSONObject;
import com.alipay.api.AlipayApiException;
import com.alipay.api.AlipayClient;
import com.alipay.api.DefaultAlipayClient;
import com.alipay.api.domain.AlipayTradePrecreateModel;
import com.alipay.api.request.AlipayTradeAppPayRequest;
import com.alipay.api.request.AlipayTradePrecreateRequest;
import com.alipay.api.response.AlipayTradeAppPayResponse;
import com.yqs.pay.entity.AlipayConfig;

public class AlipayUtil {
	
	private static Logger log  = Logger.getLogger(AlipayUtil.class);

	/**
	 * @param body 商品信息
	 * @param subject 商品名称
	 * @param out_trade_no 商户订单号
	 * @param amount 订单金额
	 * @param productCode
	 * @return
	 */
	public static String alipayOrderPay(String body,String out_trade_no,String amount){
		//实例化客户端
		AlipayClient alipayClient = new DefaultAlipayClient(AlipayConfig.URL, AlipayConfig.APP_ID, AlipayConfig.RSA_PRIVATE_KEY,AlipayConfig.FORMAT , AlipayConfig.CHARSET, AlipayConfig.ALIPAY_PUBLIC_KEY, AlipayConfig.SIGNTYPE);
		//实例化具体API对应的request类,类名称和接口名称对应,当前调用接口名称:alipay.trade.app.pay
		AlipayTradeAppPayRequest request = new AlipayTradeAppPayRequest();
		//SDK已经封装掉了公共参数,这里只需要传入业务参数。以下方法为sdk的model入参方式(model和biz_content同时存在的情况下取biz_content)。
		Map<String, Object> biz_content = new HashMap<String,Object>();
		biz_content.put("subject", AlipayConfig.subject);
		biz_content.put("out_trade_no", out_trade_no);
		biz_content.put("total_amount", amount);
		biz_content.put("product_code","QUICK_MSECURITY_PAY");
		biz_content.put("body",body);
		biz_content.put("timeout_express","30m");
		request.setBizContent(JSONObject.toJSONString(biz_content));
		request.setNotifyUrl(AlipayConfig.notify_url);	//回调地址不可以带参数
		String orderStr = "";
		try {
		        //这里和普通的接口调用不同,使用的是sdkExecute
		        AlipayTradeAppPayResponse response = alipayClient.sdkExecute(request);
		        orderStr = response.getBody();
		        log.info(orderStr);//就是orderString 可以直接给客户端请求,无需再做处理。
		    } catch (AlipayApiException e) {
		        e.printStackTrace();
		}
		return orderStr;
	}
	
	public static String alipayQrCodePay(String out_trade_no,String total_amount){
		//实例化客户端
		AlipayClient alipayClient = new DefaultAlipayClient(AlipayConfig.URL, AlipayConfig.APP_ID, AlipayConfig.RSA_PRIVATE_KEY,AlipayConfig.FORMAT , AlipayConfig.CHARSET, AlipayConfig.ALIPAY_PUBLIC_KEY, AlipayConfig.SIGNTYPE);
		AlipayTradePrecreateRequest request = new AlipayTradePrecreateRequest();
        request.setNotifyUrl(AlipayConfig.notify_url);
		AlipayTradePrecreateModel model = new AlipayTradePrecreateModel();
		request.setBizModel(model);
        model.setSubject(AlipayConfig.subject);
        model.setTotalAmount(total_amount);
        model.setStoreId("");
        model.setTimeoutExpress("90m");
        model.setOutTradeNo(out_trade_no);
	    try {
	    	String resultStr = alipayClient.execute(request).getBody();
	    	JSONObject jsonObject = JSONObject.parseObject(resultStr);
	    	String qr_code = jsonObject.getJSONObject("alipay_trade_precreate_response").getString("qr_code");
	    	log.info("二维码地址:"+qr_code);
	    	return qr_code;
	    } catch (AlipayApiException e) {
	        e.printStackTrace();
	        log.fatal("支付宝预订单异常",e);
	    }
		return null;
	}
	
}

四、项目对接过程中的问题:

    iOS调试一直不成功,一直返回ALI38173;

    然后找了一天半的时间,最后在阿里的博客上面贴了签名的字符串,说是iOS客户端的问题;

    但是重要的是前一天晚上被另外一个同事查到iOS出错的原因

五.后台开发当中需要注意以下情况:

1.需要注意对接支付宝配置信息当中的公私钥,公钥是支付宝公钥,私钥是商户私钥

2.回调地址一定是正常连接或者安全连接,不安全连接会造成无法接收到回调请求

 

    如果有感兴趣的盆友可以一起探讨支付宝支付的相关问题,共同进步;

评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值