支付寶當面付(支付寶面付是什么意思)
測試地址
項目背景
為什么想做這個 一是工作中也接觸到了支付寶,微信支付方面,二是自己也想弄個收費服務(wù),比如之后做的程序想收費可以直接讓用戶掃碼支付,而不用微信交流了。
了解什么支付適合個人支付
微信支付:需要營業(yè)執(zhí)照,個人不好弄,所以放棄。
支付寶手機支付:大多也需要營業(yè)執(zhí)照,個人不好弄,所以放棄。
爬蟲和監(jiān)聽收款手機信息:操作太復雜,爬蟲好像說也容易被封,放棄。
支付寶當面付,暫時可以支持個人不需要營業(yè)執(zhí)照,只需要店面圖片即可,所以了解到這,直接開搞。
開通支付寶當面付流程
開通 當面付(點擊下方鏈接開通)
開通 當面付
經(jīng)營類目 選擇 “百貨零售 / 其他零售 / 雜貨店”,或者其他…問題不大營業(yè)執(zhí)照 可不上傳店鋪招牌 可以拍一下身份的百貨店,或者百度找一張類似的圖 創(chuàng)建應(yīng)用并且添加支付能力
可以參考官方文檔:(或者按照我的步驟下面步驟)
創(chuàng)建應(yīng)用
創(chuàng)建應(yīng)用(點擊鏈接進入)
open.alipay.com/platform/de…
填寫相關(guān)應(yīng)用資料 應(yīng)用 添加能力
應(yīng)用 開發(fā)設(shè)置 設(shè)置 接口加簽方式,手機收到驗證碼填寫下載 支付寶開放平臺開發(fā)助手即密鑰生成工具 opendocs.alipay.com/open/291/in…
上傳剛才生成的應(yīng)用公鑰
點擊保存上傳的應(yīng)用公鑰之后,會彈窗給出支付寶的公鑰
設(shè)置應(yīng)用網(wǎng)關(guān)等
應(yīng)用 提交審核
審核一般一天左右,運氣好半天就可以
開始寫代碼
當面付,我總結(jié)流程就分兩步,1. 獲取支付二維碼,2. 支付回調(diào)。
獲取支付二維碼
public String preCreateOrder(AliPayInfo aliPayInfo) throws AlipayApiException {
AlipayClient alipayClient = aliPayBusinessConfig.getAlipayClient();
AlipayTradePrecreateRequest request = new AlipayTradePrecreateRequest();
request.setNotifyUrl("https://ggball.top/notify/ali/pay/face/notify");
JSONObject bizContent = new JSONObject();
bizContent.put("out_trade_no", aliPayInfo.getOutTradeNo());
bizContent.put("total_amount", aliPayInfo.getTotalAmount());
bizContent.put("subject", aliPayInfo.getSubject());
商品明細信息,按需傳入
//JSONArray goodsDetail = new JSONArray();
//JSONObject goods1 = new JSONObject();
//goods1.put("goods_id", "goodsNo1");
//goods1.put("goods_name", "子商品1");
//goods1.put("quantity", 1);
//goods1.put("price", 0.01);
//goodsDetail.add(goods1);
//bizContent.put("goods_detail", goodsDetail);
擴展信息,按需傳入
//JSONObject extendParams = new JSONObject();
//extendParams.put("sys_service_provider_id", "2088511833207846");
//bizContent.put("extend_params", extendParams);
結(jié)算信息,按需傳入
//JSONObject settleInfo = new JSONObject();
//JSONArray settleDetailInfos = new JSONArray();
//JSONObject settleDetail = new JSONObject();
//settleDetail.put("trans_in_type", "defaultSettle");
//settleDetail.put("amount", 0.01);
//settleDetailInfos.add(settleDetail);
//settleInfo.put("settle_detail_infos", settleDetailInfos);
//bizContent.put("settle_info", settleInfo);
二級商戶信息,按需傳入
//JSONObject subMerchant = new JSONObject();
//subMerchant.put("merchant_id", "2088000603999128");
//bizContent.put("sub_merchant", subMerchant);
業(yè)務(wù)參數(shù)信息,按需傳入
//JSONObject businessParams = new JSONObject();
//businessParams.put("busi_params_key", "busiParamsValue");
//bizContent.put("business_params", businessParams);
營銷信息,按需傳入
//JSONObject promoParams = new JSONObject();
//promoParams.put("promo_params_key", "promoParamsValue");
//bizContent.put("promo_params", promoParams);
request.setBizContent(bizContent.toString());
AlipayTradePrecreateResponse response = alipayClient.execute(request);
if(response.isSuccess()){
System.out.println("調(diào)用成功");
log.info("res:{}",response.getBody());
JSONObject jsonObject = JSONObject.parseObject(response.getBody());
return jsonObject.getJSONObject("alipay_trade_precreate_response").getString("qr_code");
} else {
log.error("res:{}",response.getBody());
System.out.println("調(diào)用失敗");
return "";
}
}
如果在本地測試的話,可以使用釘釘給的免費的內(nèi)網(wǎng)穿透工具,這里我是使用自己的服務(wù),frp內(nèi)網(wǎng)穿透到本地的?;卣{(diào)地址一定是公網(wǎng)能夠訪問到的域名,要不然回調(diào)會失敗。
支付回調(diào)
@PostMapping ("/notify")
public String preOrderNotify(HttpServletRequest request) throws AlipayApiException {
//獲取支付寶POST過來反饋信息,將異步通知中收到的待驗證所有參數(shù)都存放到map中
Map<String, String> params = new HashMap<String, String>();
Map requestParams = request.getParameterMap();
for (Iterator 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] + ",";
}
//亂碼解決,這段代碼在出現(xiàn)亂碼時使用。
//valueStr = new String(valueStr.getBytes("ISO-8859-1"), "utf-8");
params.put(name, valueStr);
}
log.info("params:{}",params);
//調(diào)用SDK驗證簽名
//公鑰驗簽示例代碼
boolean signVerified = AlipaySignature.rsaCheckV1(params, aliPayBusinessConfig.getPublicKey(), aliPayBusinessConfig.getCharset(), aliPayBusinessConfig.getSignType());
//公鑰證書驗簽示例代碼
// boolean flag = AlipaySignature.rsaCertCheckV1(params,alipayPublicCertPath,"UTF-8","RSA2");
PayBill oldPayBill = payBillService.getPayBillByNotifyId(params.get("notify_id"));
if (null != oldPayBill) {
return "success";
} else if (signVerified) {
// TODO 驗簽成功后
PayBill payBill = new PayBill();
payBill.setOrderNum(params.get("out_trade_no"));
payBill.setIsPay(true);
payBill.setNotifyId(params.get("notify_id"));
payBill.setPayerId(params.get("buyer_id"));
payBill.setSellerEmail(params.get("seller_email"));
payBill.setSellerId(params.get("seller_id"));
payBill.setTradeNo(params.get("trade_no"));
payBill.setBuyerLogonId(params.get("buyer_logon_id"));
PayBill newPayBill = payBillService.updatePayBill(payBill);
// push queue
try {
QueueCore<PayBill> billQueueCore = new QueueCore<>("NOTIFY_JOB");
billQueueCore.get("NOTIFY_JOB").push(newPayBill);
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
return "success";
//按照支付結(jié)果異步通知中的描述,對支付結(jié)果中的業(yè)務(wù)內(nèi)容進行1234二次校驗,校驗成功后在response中返回success
} else {
// TODO 驗簽失敗則記錄異常日志,并在response中返回fail.
return "fail";
}
}
這里是支付寶提供的代碼,驗簽失敗和成功可以添加自己的邏輯代碼,這里我是將結(jié)果放在隊列里,為了后續(xù)將數(shù)據(jù)保存到數(shù)據(jù)庫,將支付結(jié)果通知給我的其他服務(wù)等等。
測試截圖
測試地址
繼續(xù)閱讀
- 暫無推薦