<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          Spring Boot 接入支付寶,實(shí)戰(zhàn)來了!

          共 19937字,需瀏覽 40分鐘

           ·

          2021-05-02 14:26

          作者 | 李秀才

          來源 | blog.csdn.net/qq_33556185/article/details/110445827

          支付寶推出了新的轉(zhuǎn)賬接口alipay.fund.trans.uni.transfer(升級(jí)后安全性更高,功能更加強(qiáng)大) ,老轉(zhuǎn)賬接口alipay.fund.trans.toaccount.transfer將不再維護(hù),新老接口的一個(gè)區(qū)別就是新接口采用的證書驗(yàn)簽方式。

          使用新接口要將sdk版本升級(jí)到最新版本,博主升級(jí)時(shí)最新版本是4.10.97。

          接下來看集成步驟。

          1.將支付寶開放平臺(tái)里下載的3個(gè)證書放在resources下面

          2.寫支付寶支付的配置文件

          alipay.properties

          alipay.appId=你的應(yīng)用id
          alipay.serverUrl=https://openapi.alipay.com/gateway.do
          alipay.privateKey=你的應(yīng)用私鑰
          alipay.format=json
          alipay.charset=UTF-8
          alipay.signType=RSA2
          alipay.appCertPath=/cert/appCertPublicKey_2021001164652941.crt
          alipay.alipayCertPath=/cert/alipayCertPublicKey_RSA2.crt
          alipay.alipayRootCertPath=/cert/alipayRootCert.crt

          3.引入pom依賴

          <dependency>
               <groupId>com.alipay.sdk</groupId>
               <artifactId>alipay-sdk-java</artifactId>
               <version>4.10.97.ALL</version>
          </dependency>

          4.將配置信息注入AliPayBean

          import lombok.Data;
          import org.springframework.boot.context.properties.ConfigurationProperties;
          import org.springframework.context.annotation.PropertySource;
          import org.springframework.stereotype.Component;
           
          @Component
          @PropertySource("classpath:/production/alipay.properties")
          @ConfigurationProperties(prefix = "alipay")
          @Data
          public class AliPayBean {
              private String appId;
              private String privateKey;
              private String publicKey;
              private String serverUrl;
              private String domain;
              private String format;
              private String charset;
              private String signType;
              private String appCertPath;
              private String alipayCertPath;
              private String alipayRootCertPath;
           
          }

          5.寫配置類

          import com.alipay.api.AlipayClient;
          import com.alipay.api.CertAlipayRequest;
          import com.alipay.api.DefaultAlipayClient;
          import org.springframework.beans.factory.annotation.Autowired;
          import org.springframework.beans.factory.annotation.Value;
          import org.springframework.context.annotation.Bean;
          import org.springframework.context.annotation.Configuration;
          import org.springframework.util.FileCopyUtils;
           
          import java.io.InputStream;
           
           
          @Configuration
          public class AliConfig {
           
              @Value("${custom.http.proxyHost}")
              private String proxyHost;
              @Value("${custom.http.proxyPort}")
              private int proxyPort;
              @Value("${spring.profiles.active}")
              private String activeEnv;
           
              @Autowired
              private AliPayBean aliPayBean;
           
              @Bean(name = {"alipayClient"})
              public AlipayClient alipayClientService() throws Exception{
                  CertAlipayRequest certAlipayRequest = new CertAlipayRequest();
                  //設(shè)置網(wǎng)關(guān)地址
                  certAlipayRequest.setServerUrl(aliPayBean.getServerUrl());
                  //設(shè)置應(yīng)用Id
                  certAlipayRequest.setAppId(aliPayBean.getAppId());
                  //設(shè)置應(yīng)用私鑰
                  certAlipayRequest.setPrivateKey(aliPayBean.getPrivateKey());
                  //設(shè)置請(qǐng)求格式,固定值json
                  certAlipayRequest.setFormat(aliPayBean.getFormat());
                  //設(shè)置字符集
                  certAlipayRequest.setCharset(aliPayBean.getCharset());
                  //設(shè)置簽名類型
                  certAlipayRequest.setSignType(aliPayBean.getSignType());
                  //如果是生產(chǎn)環(huán)境或者預(yù)演環(huán)境,則使用代理模式
                  if ("prod".equals(activeEnv) || "stage".equals(activeEnv) || "test".equals(activeEnv)) {
                      //設(shè)置應(yīng)用公鑰證書路徑
                      certAlipayRequest.setCertContent(getCertContentByPath(aliPayBean.getAppCertPath()));
                      //設(shè)置支付寶公鑰證書路徑
                      certAlipayRequest.setAlipayPublicCertContent(getCertContentByPath(aliPayBean.getAlipayCertPath()));
                      //設(shè)置支付寶根證書路徑
                      certAlipayRequest.setRootCertContent(getCertContentByPath(aliPayBean.getAlipayRootCertPath()));
                      certAlipayRequest.setProxyHost(proxyHost);
                      certAlipayRequest.setProxyPort(proxyPort);
           
                  }else {
                      //local
                      String serverPath = this.getClass().getResource("/").getPath();
                      //設(shè)置應(yīng)用公鑰證書路徑
                      certAlipayRequest.setCertPath(serverPath+aliPayBean.getAppCertPath());
                      //設(shè)置支付寶公鑰證書路徑
                      certAlipayRequest.setAlipayPublicCertPath(serverPath+aliPayBean.getAlipayCertPath());
                      //設(shè)置支付寶根證書路徑
                      certAlipayRequest.setRootCertPath(serverPath+aliPayBean.getAlipayRootCertPath());
                  }
                  return new DefaultAlipayClient(certAlipayRequest);
              }
              public String getCertContentByPath(String name){
                  InputStream inputStream = null;
                  String content = null;
                  try{
                      inputStream = this.getClass().getClassLoader().getResourceAsStream(name);
                      content = new String(FileCopyUtils.copyToByteArray(inputStream));
                  }catch (Exception e){
                      e.printStackTrace();
                  }
                  return content;
              }
           
          }

          6.寫支付工具類

          import com.alipay.api.AlipayApiException;
          import com.alipay.api.AlipayClient;
          import com.alipay.api.domain.AlipayTradeAppPayModel;
          import com.alipay.api.domain.AlipayTradeQueryModel;
          import com.alipay.api.request.AlipayTradeAppPayRequest;
          import com.alipay.api.request.AlipayTradeQueryRequest;
          import com.alipay.api.response.AlipayTradeAppPayResponse;
          import com.alipay.api.response.AlipayTradeQueryResponse;
          import lombok.extern.slf4j.Slf4j;
          import org.springframework.beans.factory.annotation.Autowired;
          import org.springframework.beans.factory.annotation.Qualifier;
          import org.springframework.stereotype.Service;
          /**
           * @description:支付寶工具類
           * @Date:2020-08-26
           */
          @Slf4j
          @Service
          public class AliPayUtils {
              @Autowired
              @Qualifier("alipayClient")
              private AlipayClient alipayClient;
           
              /**
               * 交易查詢接口
               * @param request
               * @return
               * @throws Exception
               */
              public boolean isTradeQuery(AlipayTradeQueryModel model) throws AlipayApiException {
                  AlipayTradeQueryRequest request = new AlipayTradeQueryRequest();
                  request.setBizModel(model);
                  AlipayTradeQueryResponse alipayTradeQueryResponse = alipayClient.certificateExecute(request);
                  if(alipayTradeQueryResponse.isSuccess()){
                      return true;
                  } else {
                      return false;
                  }
              }
           
              /**
               * app支付
               * @param model
               * @param notifyUrl
               * @return
               * @throws AlipayApiException
               */
              public String startAppPay(AlipayTradeAppPayModel model, String notifyUrl)  throws AlipayApiException {
                  AlipayTradeAppPayRequest aliPayRequest = new AlipayTradeAppPayRequest();
                  model.setProductCode("QUICK_MSECURITY_PAY");
                  aliPayRequest.setNotifyUrl(notifyUrl);
                  aliPayRequest.setBizModel(model);
                  // 這里和普通的接口調(diào)用不同,使用的是sdkExecute
                  AlipayTradeAppPayResponse aliResponse = alipayClient.sdkExecute(aliPayRequest);
                  return aliResponse.getBody();
              }
              /**
               * 轉(zhuǎn)賬接口
               *
               * @param transferParams
               * @return AlipayFundTransToaccountTransferResponse
               */
               public AlipayFundTransUniTransferResponse doTransferNew(TransferParams transferParams) throws Exception {
           
                  String title = (StringUtils.isNotBlank(transferParams.getRemark()) ? transferParams
                          .getRemark() : "轉(zhuǎn)賬");
                  //轉(zhuǎn)賬請(qǐng)求入?yún)?br>        AlipayFundTransUniTransferRequest request = new AlipayFundTransUniTransferRequest();
                  //轉(zhuǎn)賬參數(shù)
                  BizContentForUniTransfer bizContent = new BizContentForUniTransfer();
                  bizContent.setOut_biz_no(transferParams.getOutBizNo());
                  bizContent.setTrans_amount(MathUtil.changeF2Y(Math.abs(Integer.parseInt(transferParams.getAmount()))));
                  bizContent.setProduct_code("TRANS_ACCOUNT_NO_PWD");
                  bizContent.setBiz_scene("DIRECT_TRANSFER");
                  bizContent.setOrder_title(title);
                  Participant participant = new Participant();
                  participant.setIdentity(transferParams.getPayeeAccount());
                  participant.setIdentity_type(transferParams.getPayeeType());
                  participant.setName((StringUtils.isNotBlank(transferParams.getPayeeRealName()) ? transferParams
                          .getPayeeRealName() : StringUtils.EMPTY));
                  bizContent.setPayee_info(participant);
                  bizContent.setRemark(title);
           
                  request.setBizContent(JSON.toJSONString(bizContent));
           
                  //轉(zhuǎn)賬請(qǐng)求返回
                  AlipayFundTransUniTransferResponse response = null;
                  try {
                      response = alipayClient.certificateExecute(request);
                  } catch (Exception e) {
           
                      log.info("doTransfer exception,異常信息:{}", e.toString());
           
                      log.info("doTransfer exception,支付寶返回信息:{}", JSONObject.toJSONString(response));
           
                  }
           
                  log.info("doTransfer,AlipayFundTransUniTransferResponse:{}", JSONObject.toJSONString(response));
           
                  return response;
              }
          }

          Tips:轉(zhuǎn)賬用到的類

          @Data
          public class TransferParams {
           
              /**
               * 應(yīng)用編號(hào)
               */
              private Long appId;
           
              /**
               * 創(chuàng)建人id
               */
              private Long createdBy;
           
              /**
               * 轉(zhuǎn)賬業(yè)務(wù)訂單號(hào)
               */
              private String outBizNo;
           
              /**
               * 收款方識(shí)別方式
               */
              private String payeeType;
           
              /**
               * 收款方賬號(hào),可以是支付寶userId或者支付寶loginId
               */
              private String payeeAccount;
           
              /**
               * 轉(zhuǎn)賬金額,單位分
               */
              private String amount;
           
              /**
               * 付款方名稱
               */
              private String payerShowName;
           
              /**
               * 收款方名稱
               */
              private String payeeRealName;
           
              /**
               * 備注
               */
              private String remark;
           
              /**
               * 支付寶轉(zhuǎn)賬流水號(hào)
               */
              private String orderId;
          }
          import lombok.Data;
           
          import java.math.BigDecimal;
           
          /**
           * 支付寶轉(zhuǎn)賬參數(shù)
           */
          @Data
          public class BizContentForUniTransfer {
              /**
               * 業(yè)務(wù)訂單號(hào)
               */
              private String out_biz_no;
           
              /**
               * 訂單總金額,單位為元,精確到小數(shù)點(diǎn)后兩位,
               */
              private BigDecimal trans_amount;
           
              /**
               * 業(yè)務(wù)產(chǎn)品碼,
               * 單筆無密轉(zhuǎn)賬到支付寶賬戶固定為:TRANS_ACCOUNT_NO_PWD;
               * 單筆無密轉(zhuǎn)賬到銀行卡固定為:TRANS_BANKCARD_NO_PWD;
               * 收發(fā)現(xiàn)金紅包固定為:STD_RED_PACKET;
               */
              private String product_code;
           
              /**
               * 描述特定的業(yè)務(wù)場(chǎng)景,可傳的參數(shù)如下:
               * DIRECT_TRANSFER:?jiǎn)喂P無密轉(zhuǎn)賬到支付寶/銀行卡, B2C現(xiàn)金紅包;
               * PERSONAL_COLLECTION:C2C現(xiàn)金紅包-領(lǐng)紅包
               */
              private String biz_scene;
           
              /**
               * 轉(zhuǎn)賬業(yè)務(wù)的標(biāo)題,用于在支付寶用戶的賬單里顯示
               */
              private String order_title;
           
              /**
               * 原支付寶業(yè)務(wù)單號(hào)。C2C現(xiàn)金紅包-紅包領(lǐng)取時(shí),傳紅包支付時(shí)返回的支付寶單號(hào);
               * B2C現(xiàn)金紅包、單筆無密轉(zhuǎn)賬到支付寶/銀行卡不需要該參數(shù)。
               */
              private String original_order_id;
           
              /**
               * 業(yè)務(wù)備注
               */
              private String remark;
           
              /**
               * 轉(zhuǎn)賬業(yè)務(wù)請(qǐng)求的擴(kuò)展參數(shù),支持傳入的擴(kuò)展參數(shù)如下:
               * 1、sub_biz_scene 子業(yè)務(wù)場(chǎng)景,紅包業(yè)務(wù)必傳,取值REDPACKET,C2C現(xiàn)金紅包、B2C現(xiàn)金紅包均需傳入;
               * 2、withdraw_timeliness為轉(zhuǎn)賬到銀行卡的預(yù)期到賬時(shí)間,可選(不傳入則默認(rèn)為T1),
               * 取值T0表示預(yù)期T+0到賬,取值T1表示預(yù)期T+1到賬,因到賬時(shí)效受銀行機(jī)構(gòu)處理影響,支付寶無法保證一定是T0或者T1到賬;
               */
              private String business_params;
           
              /**
               * 支付收款對(duì)象
               */
              private Participant payee_info;
          }
          @Data
          public class Participant {
              /**
               * 參與方的唯一標(biāo)識(shí)
               */
              private String identity;
           
              /**
               * 參與方的標(biāo)識(shí)類型,目前支持如下類型:
               * 1、ALIPAY_USER_ID 支付寶的會(huì)員ID
               * 2、ALIPAY_LOGON_ID:支付寶登錄號(hào),支持郵箱和手機(jī)號(hào)格式
               */
              private String identity_type;
           
              /**
               * 參與方真實(shí)姓名,如果非空,將校驗(yàn)收款支付寶賬號(hào)姓名一致性。
               * 當(dāng)identity_type=ALIPAY_LOGON_ID時(shí),本字段必填。
               */
              private String name;
          }

          1、Intellij IDEA這樣 配置注釋模板,讓你瞬間高出一個(gè)逼格!
          2、吊炸天的 Docker 圖形化工具 Portainer,必須推薦給你!
          3、最牛逼的 Java 日志框架,性能無敵,橫掃所有對(duì)手!
          4、把Redis當(dāng)作隊(duì)列來用,真的合適嗎?
          5、驚呆了,Spring Boot居然這么耗內(nèi)存!你知道嗎?
          6、全網(wǎng)最全 Java 日志框架適配方案!還有誰(shuí)不會(huì)?
          7、Spring中毒太深,離開Spring我居然連最基本的接口都不會(huì)寫了

          點(diǎn)分享

          點(diǎn)收藏

          點(diǎn)點(diǎn)贊

          點(diǎn)在看

          瀏覽 48
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          評(píng)論
          圖片
          表情
          推薦
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  99精品在线观看免费视频 | 国产成人无码免费视频 | 亚洲涩图91 | 波多野结衣免费看 | 一区二区三区四区在线 |