Showing
10 changed files
with
365 additions
and
52 deletions
@@ -50,5 +50,17 @@ public class TradeBills { | @@ -50,5 +50,17 @@ public class TradeBills { | ||
50 | //打款关联id | 50 | //打款关联id |
51 | private Integer dealRelateId = 0; | 51 | private Integer dealRelateId = 0; |
52 | 52 | ||
53 | - | 53 | + public static enum Status { |
54 | + | ||
55 | + TRANSFER_WAITING(90); | ||
56 | + | ||
57 | + private Status(int code) { | ||
58 | + this.code = code; | ||
59 | + } | ||
60 | + private int code; | ||
61 | + public int getCode() { | ||
62 | + return code; | ||
63 | + } | ||
64 | + | ||
65 | + } | ||
54 | } | 66 | } |
@@ -90,6 +90,8 @@ public class AlipayConfig { | @@ -90,6 +90,8 @@ public class AlipayConfig { | ||
90 | public static final String BLK_ALI_RSA_PUBLIC = "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCnxj/9qwVfgoUh/y2W89L6BkRAFljhNhgPdyPuBV64bfQNN1PjbCzkIM6qRdKBoLPXmKKMiFYnkd6rAoprih3/PrQEB/VsW8OoM8fxn67UDYuyBTqA23MML9q1+ilIZwBC2AQ2UBVOrFXfFl75p6/B5KsiNG9zpgmLCUYuLkxpLQIDAQAB"; | 90 | public static final String BLK_ALI_RSA_PUBLIC = "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCnxj/9qwVfgoUh/y2W89L6BkRAFljhNhgPdyPuBV64bfQNN1PjbCzkIM6qRdKBoLPXmKKMiFYnkd6rAoprih3/PrQEB/VsW8OoM8fxn67UDYuyBTqA23MML9q1+ilIZwBC2AQ2UBVOrFXfFl75p6/B5KsiNG9zpgmLCUYuLkxpLQIDAQAB"; |
91 | 91 | ||
92 | /********************/ //OUYIN | 92 | /********************/ //OUYIN |
93 | + public static final String OUYIN_EMAIL = "ouyin@yoho.cn"; | ||
94 | + public static final String OUYIN_USER_NAME = "欧印南京贸易有限公司"; | ||
93 | public static final String OUYIN_PARTNER = "2088421850636193"; | 95 | public static final String OUYIN_PARTNER = "2088421850636193"; |
94 | 96 | ||
95 | public static final String OUYIN_APPID = "2016091401906455"; | 97 | public static final String OUYIN_APPID = "2016091401906455"; |
@@ -29,6 +29,7 @@ import com.yohoufo.order.model.NotifyResponse; | @@ -29,6 +29,7 @@ import com.yohoufo.order.model.NotifyResponse; | ||
29 | import com.yohoufo.order.model.PayQueryBo; | 29 | import com.yohoufo.order.model.PayQueryBo; |
30 | import com.yohoufo.order.model.PayRefundBo; | 30 | import com.yohoufo.order.model.PayRefundBo; |
31 | import com.yohoufo.order.model.PaymentData; | 31 | import com.yohoufo.order.model.PaymentData; |
32 | +import com.yohoufo.order.model.TransferData; | ||
32 | import com.yohoufo.order.model.request.PaymentRequest; | 33 | import com.yohoufo.order.model.request.PaymentRequest; |
33 | import com.yohoufo.order.model.response.PaymentConfirmRsp; | 34 | import com.yohoufo.order.model.response.PaymentConfirmRsp; |
34 | import com.yohoufo.order.model.response.PrepayResponse; | 35 | import com.yohoufo.order.model.response.PrepayResponse; |
@@ -259,6 +260,44 @@ public class PaymentController { | @@ -259,6 +260,44 @@ public class PaymentController { | ||
259 | logger.info("[{}] reply success to alipay", out_trade_no); | 260 | logger.info("[{}] reply success to alipay", out_trade_no); |
260 | response.getWriter().print("success"); | 261 | response.getWriter().print("success"); |
261 | } | 262 | } |
263 | + | ||
264 | + @IgnoreSignature | ||
265 | + @IgnoreSession | ||
266 | + @RequestMapping(value = "/ufo_alipay_transfer_notify", method = RequestMethod.POST) | ||
267 | + public void notifyAliTransferPayment(HttpServletRequest request, HttpServletResponse response) throws IOException { | ||
268 | + alipayLogger.info("\n\n\n************************* Notify ufo_alipay_transfer_notify"); | ||
269 | + | ||
270 | + Map<String, String> params = parseParams(request.getParameterMap()); | ||
271 | + alipayLogger.info("[{}] ufo_alipay_transfer_notify Request params: {}", params); | ||
272 | + | ||
273 | + | ||
274 | + String batch_no = params.get("batch_no"); | ||
275 | + alipayLogger.info("[{}] ufo_alipay_transfer_notify notification received", batch_no); | ||
276 | + | ||
277 | + //回调验证 | ||
278 | + if(!alipayService.notifyVerify(params)) { | ||
279 | + alipayLogger.error("[{}] ufo_alipay_transfer_notify notification verify failed", batch_no); | ||
280 | + return ; | ||
281 | + } | ||
282 | + | ||
283 | + TransferData data = null; | ||
284 | + try { | ||
285 | + TransferData success = alipayService.getTransferData(params.get("success_details")); | ||
286 | + TransferData fail = alipayService.getTransferData(params.get("fail_details")); | ||
287 | + alipayLogger.info("method {} ufo_alipay_transfer_notify data is {},{}", batch_no, success, fail); | ||
288 | + if((success==null && fail==null) ||(success!=null &&fail!=null)) { | ||
289 | + alipayLogger.info("method {} ufo_alipay_transfer_notify success 和 fail 歧义", batch_no); | ||
290 | + } | ||
291 | + data = (fail == null) ? success : fail; | ||
292 | + paymentService.transferSuccess(data); | ||
293 | + } catch (Exception e) { | ||
294 | + alipayLogger.error("[{}] ufo_alipay_transfer_notify notify process failed, ex: {}", batch_no, e); | ||
295 | + return ; | ||
296 | + } | ||
297 | + | ||
298 | + logger.info("[{}] ufo_alipay_transfer_notify reply success to alipay", batch_no); | ||
299 | + response.getWriter().print("success"); | ||
300 | + } | ||
262 | 301 | ||
263 | /* @RequestMapping(params = "method=ufo.order.transferMon") | 302 | /* @RequestMapping(params = "method=ufo.order.transferMon") |
264 | public ApiResponse transferMon(@RequestParam(name = "buyerOrderCode") long buyerOrderCode, | 303 | public ApiResponse transferMon(@RequestParam(name = "buyerOrderCode") long buyerOrderCode, |
1 | +package com.yohoufo.order.model; | ||
2 | + | ||
3 | +import lombok.Data; | ||
4 | +import lombok.ToString; | ||
5 | + | ||
6 | +@Data | ||
7 | +@ToString | ||
8 | +public class TransferData { | ||
9 | + | ||
10 | + | ||
11 | + private String orderCode; | ||
12 | + private Integer transferId; | ||
13 | + private Integer tradeBillsId; | ||
14 | + private String receiveAccount; | ||
15 | + private String receiveUserName; | ||
16 | + private String money; | ||
17 | + private String status; | ||
18 | + private String message; | ||
19 | + /** 支付宝内部流水号. */ | ||
20 | + private String alipayTradeId; | ||
21 | + private String time; | ||
22 | + | ||
23 | +} |
@@ -4,6 +4,7 @@ package com.yohoufo.order.service; | @@ -4,6 +4,7 @@ package com.yohoufo.order.service; | ||
4 | import com.yohobuy.ufo.model.order.req.ManualDealRequest; | 4 | import com.yohobuy.ufo.model.order.req.ManualDealRequest; |
5 | import com.yohoufo.order.model.PayRefundBo; | 5 | import com.yohoufo.order.model.PayRefundBo; |
6 | import com.yohoufo.order.model.PaymentData; | 6 | import com.yohoufo.order.model.PaymentData; |
7 | +import com.yohoufo.order.model.TransferData; | ||
7 | import com.yohoufo.order.model.request.PaymentRequest; | 8 | import com.yohoufo.order.model.request.PaymentRequest; |
8 | import com.yohoufo.order.model.request.TransferMoneyRequest; | 9 | import com.yohoufo.order.model.request.TransferMoneyRequest; |
9 | import com.yohoufo.order.model.response.PaymentConfirmRsp; | 10 | import com.yohoufo.order.model.response.PaymentConfirmRsp; |
@@ -47,6 +48,7 @@ public interface IPaymentService { | @@ -47,6 +48,7 @@ public interface IPaymentService { | ||
47 | */ | 48 | */ |
48 | void paySuccess(PaymentData paymentData); | 49 | void paySuccess(PaymentData paymentData); |
49 | 50 | ||
51 | + void transferSuccess(TransferData transferData); | ||
50 | 52 | ||
51 | /** | 53 | /** |
52 | * 订单退款 | 54 | * 订单退款 |
@@ -23,6 +23,7 @@ import com.yohoufo.order.constants.RefundContant; | @@ -23,6 +23,7 @@ import com.yohoufo.order.constants.RefundContant; | ||
23 | import com.yohoufo.order.model.PayQueryBo; | 23 | import com.yohoufo.order.model.PayQueryBo; |
24 | import com.yohoufo.order.model.PayRefundBo; | 24 | import com.yohoufo.order.model.PayRefundBo; |
25 | import com.yohoufo.order.model.PaymentData; | 25 | import com.yohoufo.order.model.PaymentData; |
26 | +import com.yohoufo.order.model.TransferData; | ||
26 | import com.yohoufo.order.model.request.PaymentRequest; | 27 | import com.yohoufo.order.model.request.PaymentRequest; |
27 | import com.yohoufo.order.model.request.TranseferCellNode; | 28 | import com.yohoufo.order.model.request.TranseferCellNode; |
28 | import com.yohoufo.order.model.request.TransferMoneyRequest; | 29 | import com.yohoufo.order.model.request.TransferMoneyRequest; |
@@ -53,6 +54,7 @@ import org.springframework.stereotype.Service; | @@ -53,6 +54,7 @@ import org.springframework.stereotype.Service; | ||
53 | 54 | ||
54 | import java.math.BigDecimal; | 55 | import java.math.BigDecimal; |
55 | import java.util.Date; | 56 | import java.util.Date; |
57 | +import java.util.Map; | ||
56 | import java.util.Objects; | 58 | import java.util.Objects; |
57 | import java.util.function.BiFunction; | 59 | import java.util.function.BiFunction; |
58 | 60 | ||
@@ -329,6 +331,71 @@ public class PaymentServiceImpl implements IPaymentService { | @@ -329,6 +331,71 @@ public class PaymentServiceImpl implements IPaymentService { | ||
329 | logger.info("paySuccess finished. orderCode is {}", orderCode); | 331 | logger.info("paySuccess finished. orderCode is {}", orderCode); |
330 | abstractOrderService.processAfterPay(orderInfo); | 332 | abstractOrderService.processAfterPay(orderInfo); |
331 | } | 333 | } |
334 | + | ||
335 | + @Override | ||
336 | + public void transferSuccess(TransferData transferData) { | ||
337 | + int now = (int) (System.currentTimeMillis()/1000); | ||
338 | + Integer tradeBillsId = transferData.getTradeBillsId(); | ||
339 | + Integer transferId = transferData.getTransferId(); | ||
340 | + String orderCode = transferData.getOrderCode(); | ||
341 | + | ||
342 | + TradeBills tradeBills = tradeBillsMapper.selectByPrimaryKey(tradeBillsId); | ||
343 | + if (tradeBills == null) { | ||
344 | + throw new ServiceException(400, "transferSuccess:流水不存在"); | ||
345 | + } | ||
346 | + if (tradeBills.getTradeStatus() != TradeBills.Status.TRANSFER_WAITING.getCode()) { | ||
347 | + throw new ServiceException(400, "transferSuccess:该流水不是异步转账的"); | ||
348 | + } | ||
349 | + OrdersPayTransfer transfer = ordersPayTransferMapper.selectByPrimaryKey(transferId); | ||
350 | + if (transfer == null) { | ||
351 | + throw new ServiceException(400, "transferSuccess:转账记录不存在"); | ||
352 | + } | ||
353 | + if (transfer.getStatus() == 1) { | ||
354 | + throw new ServiceException(400, "transferSuccess:转账记录已经成功"); | ||
355 | + } | ||
356 | + logger.info("transferSuccess 参数 tradeBillsId={}, tradeBillsId={}, orderCode={}", tradeBillsId, tradeBillsId, orderCode); | ||
357 | + if(StringUtils.equals("S", transferData.getStatus())) { | ||
358 | + // 更新成OK | ||
359 | + TradeBills success = new TradeBills(); | ||
360 | + success.setId(tradeBills.getId()); | ||
361 | + success.setDealStatus(1); | ||
362 | + | ||
363 | + if (tradeBillsMapper.updateToOkByPrimaryKey(success) == 0) { | ||
364 | + logger.warn("transferSuccess 流水已经被并发处理过 tradeBillsId={}, tradeBillsId={}, orderCode={}", tradeBillsId, tradeBillsId, orderCode); | ||
365 | + return; | ||
366 | + } | ||
367 | + | ||
368 | + logger.info("transferSuccess 旧流水更新成功,准备加新流水 tradeBillsId={}, tradeBillsId={}, orderCode={}", tradeBillsId, tradeBillsId, orderCode); | ||
369 | + // 加新流水 | ||
370 | + tradeBills.setDealRelateId(tradeBills.getId()); | ||
371 | + tradeBills.setId(null); | ||
372 | + tradeBills.setTradeStatus(100); | ||
373 | + tradeBills.setCreateTime(now); | ||
374 | + addTradeBills(tradeBills); | ||
375 | + | ||
376 | + logger.info("transferSuccess 加新流水成功,准备修改转账状态 tradeBillsId={}, tradeBillsId={}, orderCode={}", tradeBillsId, tradeBillsId, orderCode); | ||
377 | + OrdersPayTransfer newTransfer = new OrdersPayTransfer(); | ||
378 | + newTransfer.setId(transfer.getId()); | ||
379 | + newTransfer.setStatus(1); | ||
380 | + newTransfer.setUpdateTime(now); | ||
381 | + ordersPayTransferMapper.updateByPrimaryKeySelective(newTransfer); | ||
382 | + logger.info("transferSuccess 修改转账状态成功 tradeBillsId={}, tradeBillsId={}, orderCode={}", tradeBillsId, tradeBillsId, orderCode); | ||
383 | + } else { | ||
384 | + TradeBills fail = new TradeBills(); | ||
385 | + fail.setId(tradeBills.getId()); | ||
386 | + fail.setDealStatus(0); | ||
387 | + fail.setTradeStatus(299); | ||
388 | + tradeBillsMapper.updateToOkByPrimaryKey(fail); | ||
389 | + logger.info("transferSuccess 旧流水(失败)更新成功,准备改转账表 tradeBillsId={}, tradeBillsId={}, orderCode={}", tradeBillsId, tradeBillsId, orderCode); | ||
390 | + | ||
391 | + OrdersPayTransfer newTransfer = new OrdersPayTransfer(); | ||
392 | + newTransfer.setId(transfer.getId()); | ||
393 | + newTransfer.setStatus(3); | ||
394 | + newTransfer.setUpdateTime(now); | ||
395 | + ordersPayTransferMapper.updateByPrimaryKeySelective(newTransfer); | ||
396 | + logger.info("transferSuccess 转账表(失败)更新成功 tradeBillsId={}, tradeBillsId={}, orderCode={}", tradeBillsId, tradeBillsId, orderCode); | ||
397 | + } | ||
398 | + } | ||
332 | 399 | ||
333 | private OrdersPay saveOrdersPay(PaymentData paymentData, long orderType, OrderInfo orderInfo) { | 400 | private OrdersPay saveOrdersPay(PaymentData paymentData, long orderType, OrderInfo orderInfo) { |
334 | 401 | ||
@@ -553,30 +620,8 @@ public class PaymentServiceImpl implements IPaymentService { | @@ -553,30 +620,8 @@ public class PaymentServiceImpl implements IPaymentService { | ||
553 | } | 620 | } |
554 | int now = (int) (System.currentTimeMillis()/1000); | 621 | int now = (int) (System.currentTimeMillis()/1000); |
555 | // 查看是否已经有转账记录 | 622 | // 查看是否已经有转账记录 |
556 | - OrdersPayTransfer exist = ordersPayTransferMapper.selectByBuyerOrderCode(buyerOrderCode); | ||
557 | - if (exist != null) { | ||
558 | - logger.warn("transferMonErr OrdersPayTransfer has exist, orderCode is {}", buyerOrderCode); | ||
559 | - throw new ServiceException(400, "订单已经处理过"); | ||
560 | - } | ||
561 | - | ||
562 | - OrdersPayTransfer transfer = new OrdersPayTransfer(); | ||
563 | - transfer.setBuyerOrderCode(buyerOrderCode); | ||
564 | - transfer.setSellerOrderCode(sellerOrderCode); | ||
565 | - transfer.setAlipayTradeId(""); | ||
566 | - transfer.setAlipayTradeResult(""); | ||
567 | - transfer.setTransferType(transferCase.getCode()); | ||
568 | - transfer.setUid(targetUid); | ||
569 | - transfer.setAmount(BigDecimal.ZERO); | ||
570 | - transfer.setCreateTime(now); | ||
571 | - transfer.setStatus(0); | ||
572 | - | ||
573 | - try { | ||
574 | - logger.info("transferMon插入初始化转账信息buyerOrderCode is {}, sellerOrderCode is {}", buyerOrderCode, sellerOrderCode); | ||
575 | - ordersPayTransferMapper.insert(transfer); | ||
576 | - } catch (Exception e) { | ||
577 | - logger.warn("transferMonErr insert ordersPayTransfer failed, orderCode is {}, msg is {}", buyerOrderCode, e.getMessage()); | ||
578 | - throw new ServiceException(400, "交易记录创建失败"); | ||
579 | - } | 623 | + checkTransferExist(buyerOrderCode); |
624 | + OrdersPayTransfer transfer = createTransfer(buyerOrderCode, sellerOrderCode, transferCase.getCode(), null, targetUid, BigDecimal.ZERO, now); | ||
580 | 625 | ||
581 | // 增加流水记录 | 626 | // 增加流水记录 |
582 | TradeBills record = new TradeBills(); | 627 | TradeBills record = new TradeBills(); |
@@ -686,31 +731,8 @@ public class PaymentServiceImpl implements IPaymentService { | @@ -686,31 +731,8 @@ public class PaymentServiceImpl implements IPaymentService { | ||
686 | 731 | ||
687 | int now = (int) (System.currentTimeMillis()/1000); | 732 | int now = (int) (System.currentTimeMillis()/1000); |
688 | // 查看是否已经有转账记录 | 733 | // 查看是否已经有转账记录 |
689 | - OrdersPayTransfer exist = ordersPayTransferMapper.selectByBuyerOrderCode(orderCode); | ||
690 | - if (exist != null) { | ||
691 | - logger.warn("transAllEarnestErr OrdersPayTransfer has exist, orderCode is {}", orderCode); | ||
692 | - throw new ServiceException(400, "订单已经处理过"); | ||
693 | - } | ||
694 | - | ||
695 | - OrdersPayTransfer transfer = new OrdersPayTransfer(); | ||
696 | - transfer.setBuyerOrderCode(orderCode); | ||
697 | - transfer.setSellerOrderCode(orderCode); | ||
698 | - transfer.setAlipayTradeId(""); | ||
699 | - transfer.setAlipayTradeResult(""); | ||
700 | - transfer.setAlipayAccount(alipayAccount); | ||
701 | - transfer.setTransferType(6); | ||
702 | - transfer.setUid(uid); | ||
703 | - transfer.setAmount(amount); | ||
704 | - transfer.setCreateTime(now); | ||
705 | - transfer.setStatus(0); | ||
706 | - | ||
707 | - try { | ||
708 | - logger.info("transAllEarnest插入初始化转账信息orderCode is {}", orderCode); | ||
709 | - ordersPayTransferMapper.insert(transfer); | ||
710 | - } catch (Exception e) { | ||
711 | - logger.warn("transAllEarnestErr insert ordersPayTransfer failed, orderCode is {}, msg is {}", orderCode, e.getMessage()); | ||
712 | - throw new ServiceException(400, "交易记录创建失败"); | ||
713 | - } | 734 | + checkTransferExist(orderCode); |
735 | + OrdersPayTransfer transfer = createTransfer(orderCode, orderCode, 6, alipayAccount, uid, amount, now); | ||
714 | 736 | ||
715 | // 增加流水记录 | 737 | // 增加流水记录 |
716 | TradeBills record = new TradeBills(); | 738 | TradeBills record = new TradeBills(); |
@@ -986,7 +1008,18 @@ public class PaymentServiceImpl implements IPaymentService { | @@ -986,7 +1008,18 @@ public class PaymentServiceImpl implements IPaymentService { | ||
986 | if (transfer == null || transfer.getStatus() == 1) { | 1008 | if (transfer == null || transfer.getStatus() == 1) { |
987 | throw new ServiceException(400, "转账记录已成功转账,流水id=" + tradeBillsId); | 1009 | throw new ServiceException(400, "转账记录已成功转账,流水id=" + tradeBillsId); |
988 | } | 1010 | } |
989 | - | 1011 | + |
1012 | + if(exceedMillion()) { | ||
1013 | + Map<String, String> mapResult = transferWhenExceedMillion(transfer.getId(), preSuccess, orderCode, account, amount, now); | ||
1014 | + String resultStr = JSON.toJSONString(mapResult); | ||
1015 | + jsonObject = JSON.parseObject(resultStr); | ||
1016 | + if(!StringUtils.equals("T", mapResult.get("is_success"))) { | ||
1017 | + throw new ServiceException(500, "转账失败:返回={}" + resultStr); | ||
1018 | + } else { | ||
1019 | + return; | ||
1020 | + } | ||
1021 | + } | ||
1022 | + | ||
990 | jsonObject = alipayService.transferMoney(Long.toString(orderCode), account.getAlipayId(), account.getAlipayAccount(), amount); | 1023 | jsonObject = alipayService.transferMoney(Long.toString(orderCode), account.getAlipayId(), account.getAlipayAccount(), amount); |
991 | if (jsonObject == null) { | 1024 | if (jsonObject == null) { |
992 | logger.warn("manualDeal 转账失败 , req is {}", req); | 1025 | logger.warn("manualDeal 转账失败 , req is {}", req); |
@@ -1007,6 +1040,15 @@ public class PaymentServiceImpl implements IPaymentService { | @@ -1007,6 +1040,15 @@ public class PaymentServiceImpl implements IPaymentService { | ||
1007 | tradeBills.setTradeStatus(100); | 1040 | tradeBills.setTradeStatus(100); |
1008 | tradeBills.setCreateTime(now); | 1041 | tradeBills.setCreateTime(now); |
1009 | addTradeBills(tradeBills); | 1042 | addTradeBills(tradeBills); |
1043 | + } else if(exceedMillion(jsonObject)) { | ||
1044 | + Map<String, String> mapResult = transferWhenExceedMillion(transfer.getId(), tradeBills, orderCode, account, amount, now); | ||
1045 | + String resultStr = JSON.toJSONString(mapResult); | ||
1046 | + jsonObject = JSON.parseObject(resultStr); | ||
1047 | + if(!StringUtils.equals("T", mapResult.get("is_success"))) { | ||
1048 | + throw new ServiceException(500, "转账失败:返回={}" + resultStr); | ||
1049 | + } else { | ||
1050 | + return; | ||
1051 | + } | ||
1010 | } else { | 1052 | } else { |
1011 | logger.warn("manualDealErr 返回code或者order_id不是成功状态,code={}, orderId={}", code, orderId); | 1053 | logger.warn("manualDealErr 返回code或者order_id不是成功状态,code={}, orderId={}", code, orderId); |
1012 | // 上报 | 1054 | // 上报 |
@@ -1031,6 +1073,81 @@ public class PaymentServiceImpl implements IPaymentService { | @@ -1031,6 +1073,81 @@ public class PaymentServiceImpl implements IPaymentService { | ||
1031 | logger.info("manualDeal转账结束, tradeBillsId is {}!", tradeBillsId); | 1073 | logger.info("manualDeal转账结束, tradeBillsId is {}!", tradeBillsId); |
1032 | } | 1074 | } |
1033 | } | 1075 | } |
1076 | + | ||
1077 | + | ||
1078 | + private Map<String, String> transferWhenExceedMillion(Integer transferId, TradeBills tradeBills, long orderCode, AuthorizeResultRespVO account, | ||
1079 | + BigDecimal amount, int now) throws Exception { | ||
1080 | + Map<String, String> mapResult = alipayService.transferMoneyWhenExceedMillion(Long.toString(orderCode), | ||
1081 | + transferId + "_" + tradeBills.getId(), account.getAlipayId(), account.getAlipayAccount(), | ||
1082 | + account.getCertName(), amount); | ||
1083 | + logger.info("manualDeal 转账阿里接口(超过100万)返回 {}", mapResult); | ||
1084 | + // success to wait | ||
1085 | + if (StringUtils.equals("T", mapResult.get("is_success"))) { | ||
1086 | + // TODO 加新流水 | ||
1087 | + tradeBills.setDealRelateId(tradeBills.getId()); | ||
1088 | + tradeBills.setId(null); | ||
1089 | + tradeBills.setTradeStatus(100); | ||
1090 | + tradeBills.setCreateTime(now); | ||
1091 | + addTradeBills(tradeBills); | ||
1092 | + | ||
1093 | + tradeBills.setDealStatus(0); | ||
1094 | + tradeBills.setTradeStatus(99); | ||
1095 | + // wait | ||
1096 | + tradeBillsMapper.updateToOkByPrimaryKey(tradeBills); | ||
1097 | + } | ||
1098 | + return mapResult; | ||
1099 | + } | ||
1100 | + | ||
1101 | + private boolean exceedMillion(JSONObject jsonObject) { | ||
1102 | + // {"msg":"Business Failed","code":"40004","sub_msg":"单日最多可转100万元","sub_code":"EXCEED_LIMIT_DM_MAX_AMOUNT"} | ||
1103 | + if (StringUtils.equals("40004", jsonObject.getString("code")) | ||
1104 | + && StringUtils.equals("EXCEED_LIMIT_DM_MAX_AMOUNT", jsonObject.getString("sub_code"))) { | ||
1105 | + exceedMillion = true; | ||
1106 | + return true; | ||
1107 | + } | ||
1108 | + return false; | ||
1109 | + } | ||
1110 | + private boolean exceedMillion() { | ||
1111 | + return exceedMillion; | ||
1112 | + } | ||
1113 | + | ||
1114 | + private volatile boolean exceedMillion = false; | ||
1115 | + | ||
1116 | + private void checkTransferExist(long orderCode) { | ||
1117 | + // 查看是否已经有转账记录 | ||
1118 | + OrdersPayTransfer exist = ordersPayTransferMapper.selectByBuyerOrderCode(orderCode); | ||
1119 | + if (exist != null) { | ||
1120 | + logger.warn("OrdersPayTransfer has exist, orderCode is {}", orderCode); | ||
1121 | + throw new ServiceException(400, "订单已经处理过"); | ||
1122 | + } | ||
1123 | + } | ||
1124 | + | ||
1125 | + private OrdersPayTransfer createTransfer(long buyerOrderCode, long sellerOrderCode, Integer transferType, String alipayAccount, | ||
1126 | + Integer uid, BigDecimal amount, int time) { | ||
1127 | + OrdersPayTransfer transfer = new OrdersPayTransfer(); | ||
1128 | + transfer.setBuyerOrderCode(buyerOrderCode); | ||
1129 | + transfer.setSellerOrderCode(sellerOrderCode); | ||
1130 | + transfer.setAlipayTradeId(""); | ||
1131 | + transfer.setAlipayTradeResult(""); | ||
1132 | + transfer.setAlipayAccount(alipayAccount); | ||
1133 | + transfer.setTransferType(transferType); | ||
1134 | + transfer.setUid(uid); | ||
1135 | + transfer.setAmount(amount); | ||
1136 | + transfer.setCreateTime(time); | ||
1137 | + transfer.setStatus(0); | ||
1138 | + | ||
1139 | + try { | ||
1140 | + logger.info("转账 插入初始化转账信息 buyerOrderCode is {},sellerOrderCode is {}", buyerOrderCode, sellerOrderCode); | ||
1141 | + ordersPayTransferMapper.insert(transfer); | ||
1142 | + return transfer; | ||
1143 | + } catch (Exception e) { | ||
1144 | + logger.warn( | ||
1145 | + "transferCreateErr insert ordersPayTransfer failed, buyerOrderCode is {},sellerOrderCode is {}, msg is {}", | ||
1146 | + buyerOrderCode, sellerOrderCode, e.getMessage()); | ||
1147 | + throw new ServiceException(400, "交易记录创建失败"); | ||
1148 | + } | ||
1149 | + } | ||
1150 | + | ||
1034 | 1151 | ||
1035 | public PayQueryBo queryTransferResult(String buyerOrderCode) { | 1152 | public PayQueryBo queryTransferResult(String buyerOrderCode) { |
1036 | return alipayService.transferQuery(buyerOrderCode); | 1153 | return alipayService.transferQuery(buyerOrderCode); |
@@ -31,7 +31,15 @@ public class AlipayOuyinService extends AlipayServiceAbstract { | @@ -31,7 +31,15 @@ public class AlipayOuyinService extends AlipayServiceAbstract { | ||
31 | return AlipayConfig.OUYIN_APPID; | 31 | return AlipayConfig.OUYIN_APPID; |
32 | } | 32 | } |
33 | 33 | ||
34 | + @Override | ||
35 | + protected String getAccountUserName() { | ||
36 | + return AlipayConfig.OUYIN_USER_NAME; | ||
37 | + } | ||
34 | 38 | ||
39 | + @Override | ||
40 | + protected String getAccountEmail() { | ||
41 | + return AlipayConfig.OUYIN_EMAIL; | ||
42 | + } | ||
35 | 43 | ||
36 | 44 | ||
37 | } | 45 | } |
@@ -9,6 +9,7 @@ import com.yohoufo.common.utils.DateUtil; | @@ -9,6 +9,7 @@ import com.yohoufo.common.utils.DateUtil; | ||
9 | import com.yohoufo.common.utils.HttpClient; | 9 | import com.yohoufo.common.utils.HttpClient; |
10 | import com.yohoufo.common.utils.MD5Utils; | 10 | import com.yohoufo.common.utils.MD5Utils; |
11 | import com.yohoufo.common.utils.RSAUtils; | 11 | import com.yohoufo.common.utils.RSAUtils; |
12 | +import com.yohoufo.common.utils.WXUtil; | ||
12 | import com.yohoufo.order.config.AlipayConfig; | 13 | import com.yohoufo.order.config.AlipayConfig; |
13 | import com.yohoufo.order.constants.RefundContant; | 14 | import com.yohoufo.order.constants.RefundContant; |
14 | import com.yohoufo.order.model.*; | 15 | import com.yohoufo.order.model.*; |
@@ -22,6 +23,7 @@ import org.springframework.beans.factory.annotation.Value; | @@ -22,6 +23,7 @@ import org.springframework.beans.factory.annotation.Value; | ||
22 | import java.io.UnsupportedEncodingException; | 23 | import java.io.UnsupportedEncodingException; |
23 | import java.math.BigDecimal; | 24 | import java.math.BigDecimal; |
24 | import java.net.URLEncoder; | 25 | import java.net.URLEncoder; |
26 | +import java.text.SimpleDateFormat; | ||
25 | import java.util.*; | 27 | import java.util.*; |
26 | 28 | ||
27 | public abstract class AlipayServiceAbstract extends AbstractPayService { | 29 | public abstract class AlipayServiceAbstract extends AbstractPayService { |
@@ -41,11 +43,22 @@ public abstract class AlipayServiceAbstract extends AbstractPayService { | @@ -41,11 +43,22 @@ public abstract class AlipayServiceAbstract extends AbstractPayService { | ||
41 | protected abstract String getAppId(); | 43 | protected abstract String getAppId(); |
42 | 44 | ||
43 | protected abstract String getPartnerId(); | 45 | protected abstract String getPartnerId(); |
46 | + | ||
47 | + protected String getAccountUserName() { | ||
48 | + return ""; | ||
49 | + } | ||
50 | + | ||
51 | + protected String getAccountEmail() { | ||
52 | + return ""; | ||
53 | + } | ||
44 | 54 | ||
45 | 55 | ||
46 | 56 | ||
47 | @Value("${alipay.notifyurl}") | 57 | @Value("${alipay.notifyurl}") |
48 | private String notifyURL; | 58 | private String notifyURL; |
59 | + | ||
60 | + @Value("${alipay.transfer.notifyurl}") | ||
61 | + private String transferNotifyURL; | ||
49 | 62 | ||
50 | 63 | ||
51 | // public JSONObject prepayRequest(OrderInfo orderInfo){ | 64 | // public JSONObject prepayRequest(OrderInfo orderInfo){ |
@@ -155,6 +168,29 @@ public abstract class AlipayServiceAbstract extends AbstractPayService { | @@ -155,6 +168,29 @@ public abstract class AlipayServiceAbstract extends AbstractPayService { | ||
155 | return result; | 168 | return result; |
156 | } | 169 | } |
157 | 170 | ||
171 | + /** | ||
172 | + * 转账功能 | ||
173 | + * @param transferOrderCode | ||
174 | + * @param alipayAccount | ||
175 | + * @param transferAmount | ||
176 | + * @return | ||
177 | + * @throws Exception | ||
178 | + */ | ||
179 | + public Map<String, String> transferMoneyWhenExceedMillion(String transferOrderCode, String businessId, String alipayUid, String alipayAccount, String userName, BigDecimal transferAmount) throws Exception{ | ||
180 | + | ||
181 | + Map<String, String> queryParams = buildTransferParamsWhenExceedMillion(transferOrderCode, businessId, alipayUid, alipayAccount, userName, transferAmount); | ||
182 | + String respTxt = sendOpenApiRequestWithException(transferOrderCode, queryParams); | ||
183 | + | ||
184 | + Map<String, String> result; | ||
185 | + | ||
186 | + if (StringUtils.isNotBlank(respTxt)){ | ||
187 | + result = WXUtil.parseWXPayXml(respTxt); | ||
188 | + } else { | ||
189 | + result = new HashMap<>(); | ||
190 | + } | ||
191 | + return result; | ||
192 | + } | ||
193 | + | ||
158 | public PayQueryBo transferQuery(String buyerOrderCode) { | 194 | public PayQueryBo transferQuery(String buyerOrderCode) { |
159 | String tradeNo = buyerOrderCode; | 195 | String tradeNo = buyerOrderCode; |
160 | Map<String, String> queryParams = buildAlipayTransferQueryParams(tradeNo); | 196 | Map<String, String> queryParams = buildAlipayTransferQueryParams(tradeNo); |
@@ -313,6 +349,45 @@ public abstract class AlipayServiceAbstract extends AbstractPayService { | @@ -313,6 +349,45 @@ public abstract class AlipayServiceAbstract extends AbstractPayService { | ||
313 | params.put("sign", RSAUtils.sign(preSignStr, getRsaPrivateKey(), AlipayConfig.input_charset)); | 349 | params.put("sign", RSAUtils.sign(preSignStr, getRsaPrivateKey(), AlipayConfig.input_charset)); |
314 | return params; | 350 | return params; |
315 | } | 351 | } |
352 | + | ||
353 | + /** | ||
354 | + * 单笔转账 | ||
355 | + * @param orderData | ||
356 | + * @return | ||
357 | + */ | ||
358 | + private Map<String, String> buildTransferParamsWhenExceedMillion(String transferOrderCode, String businessId, String alipayUid, String alipayAccount, String userName, BigDecimal transferAmount) { | ||
359 | + Map<String, String> params = new HashMap<String, String>(); | ||
360 | + params.put("service", "batch_trans_notify_no_pwd"); | ||
361 | + params.put("partner", getPartnerId()); | ||
362 | + params.put("_input_charset", AlipayConfig.input_charset); | ||
363 | + params.put("notify_url", transferNotifyURL); | ||
364 | + params.put("account_name", getAccountUserName()); | ||
365 | + | ||
366 | + params.put("batch_no", transferOrderCode); | ||
367 | + params.put("batch_num", "1"); | ||
368 | + params.put("batch_fee", transferAmount.toString()); | ||
369 | + params.put("email", getAccountEmail()); | ||
370 | + | ||
371 | + StringBuilder detailAppender = new StringBuilder(); | ||
372 | + detailAppender.append(businessId).append("^"); | ||
373 | + if (StringUtils.isNotBlank(alipayUid)) { | ||
374 | + // 流水号1^收款方UserId1^付款金额1^备注说明1 | ||
375 | + params.put("detail_version", "1.1"); | ||
376 | + detailAppender.append(alipayUid).append("^"); | ||
377 | + } else { | ||
378 | + // 流水号1^收款方账号1^收款账号姓名1^付款金额1^备注说明1 | ||
379 | + params.put("detail_version", "1.0"); | ||
380 | + detailAppender.append(alipayAccount).append("^").append(userName).append("^"); | ||
381 | + } | ||
382 | + params.put("detail_data", detailAppender.toString()); | ||
383 | + detailAppender.append(transferAmount).append("^UFO_ORDER"); | ||
384 | + | ||
385 | + | ||
386 | + String preSignStr = getOpenApiSignString(params); | ||
387 | + params.put("sign", RSAUtils.sign(preSignStr, getRsaPrivateKey(), AlipayConfig.input_charset)); | ||
388 | + params.put("sign_type", "RSA"); | ||
389 | + return params; | ||
390 | + } | ||
316 | 391 | ||
317 | 392 | ||
318 | /** | 393 | /** |
@@ -405,6 +480,38 @@ public abstract class AlipayServiceAbstract extends AbstractPayService { | @@ -405,6 +480,38 @@ public abstract class AlipayServiceAbstract extends AbstractPayService { | ||
405 | } | 480 | } |
406 | return payData; | 481 | return payData; |
407 | } | 482 | } |
483 | + | ||
484 | + public TransferData getTransferData(String data) { | ||
485 | + if (StringUtils.isBlank(data)) { | ||
486 | + return null; | ||
487 | + } | ||
488 | + if (data.endsWith("|")) { | ||
489 | + data = data.substring(0, data.length() - 1); | ||
490 | + } | ||
491 | + String[] dataArray = data.split("^"); | ||
492 | + if (dataArray.length != 8) { | ||
493 | + logger.error("[{}] getTransferData 支付宝回调数据字段个数有误", data); | ||
494 | + return null; | ||
495 | + } | ||
496 | + // 1流水号^2收款方账号^3收款账号姓名^4付款金额^5成功标识(S)^6成功原因(null)^7支付宝内部流水号^8完成时间 | ||
497 | + try { | ||
498 | + TransferData transferData = new TransferData(); | ||
499 | + String[] transferIdAndTradeBillId = dataArray[0].split("_"); | ||
500 | + transferData.setTransferId(new Integer(transferIdAndTradeBillId[0])); | ||
501 | + transferData.setTradeBillsId(new Integer(transferIdAndTradeBillId[1])); | ||
502 | + transferData.setReceiveAccount(dataArray[1]); | ||
503 | + transferData.setReceiveUserName(dataArray[2]); | ||
504 | + transferData.setMoney(dataArray[3]); | ||
505 | + transferData.setStatus(dataArray[4]); | ||
506 | + transferData.setMessage(dataArray[5]); | ||
507 | + transferData.setAlipayTradeId(dataArray[6]); | ||
508 | + transferData.setTime(dataArray[7]); | ||
509 | + return transferData; | ||
510 | + } catch (NumberFormatException e) { | ||
511 | + logger.error("[{}] getTransferData 支付宝回调数据格式有误", data); | ||
512 | + return null; | ||
513 | + } | ||
514 | + } | ||
408 | 515 | ||
409 | 516 | ||
410 | public boolean notifyVerify(Map<String, String> paramsMap) { | 517 | public boolean notifyVerify(Map<String, String> paramsMap) { |
@@ -81,6 +81,8 @@ wechat.notifyurl=http://testapi.yohops.com/payment/weixin_notify | @@ -81,6 +81,8 @@ wechat.notifyurl=http://testapi.yohops.com/payment/weixin_notify | ||
81 | 81 | ||
82 | alipay.notifyurl=http://testapi.yohops.com/payment/alipay_notify | 82 | alipay.notifyurl=http://testapi.yohops.com/payment/alipay_notify |
83 | 83 | ||
84 | +alipay.transfer.notifyurl=http://testapi.yohops.com/payment/alipay_transfer_notify | ||
85 | + | ||
84 | erp-gateway.url=http://java-yoho-erp-gateway.test3.ingress.dev.yohocorp.com/erp-gateway | 86 | erp-gateway.url=http://java-yoho-erp-gateway.test3.ingress.dev.yohocorp.com/erp-gateway |
85 | 87 | ||
86 | redis.readonly.proxy.address=192.168.102.45 | 88 | redis.readonly.proxy.address=192.168.102.45 |
@@ -119,7 +121,7 @@ uic.url=http://java-yoho-uic.test3.ingress.dev.yohocorp.com/uic | @@ -119,7 +121,7 @@ uic.url=http://java-yoho-uic.test3.ingress.dev.yohocorp.com/uic | ||
119 | yoho.message.controller.url=http://message-controller.yohoops.org/yoho-message-controller | 121 | yoho.message.controller.url=http://message-controller.yohoops.org/yoho-message-controller |
120 | 122 | ||
121 | #rabbit address for transaction compensate | 123 | #rabbit address for transaction compensate |
122 | -rabbit_host=192.168.102.45:5672 | 124 | +rabbit_host=192.168.104.199:30005 |
123 | rabbit_user=yoho | 125 | rabbit_user=yoho |
124 | rabbit_password=yoho | 126 | rabbit_password=yoho |
125 | 127 |
@@ -62,6 +62,7 @@ wechat.app.appid=wx049fdaa3ba9cdd7a | @@ -62,6 +62,7 @@ wechat.app.appid=wx049fdaa3ba9cdd7a | ||
62 | 62 | ||
63 | wechat.notifyurl=${wechat.notifyurl} | 63 | wechat.notifyurl=${wechat.notifyurl} |
64 | alipay.notifyurl=${alipay.notifyurl} | 64 | alipay.notifyurl=${alipay.notifyurl} |
65 | +alipay.transfer.notifyurl=${alipay.transfer.notifyurl} | ||
65 | 66 | ||
66 | order.seller.earnestmoney.min=${order.seller.earnestmoney.min} | 67 | order.seller.earnestmoney.min=${order.seller.earnestmoney.min} |
67 | order.seller.earnestmoney.max=${order.seller.earnestmoney.max} | 68 | order.seller.earnestmoney.max=${order.seller.earnestmoney.max} |
-
Please register or login to post a comment