From 4c5408d57d27aa913911010b08dfda1def0f35e1 Mon Sep 17 00:00:00 2001 From: Jack <46790855@qq.com> Date: Fri, 30 May 2025 01:35:23 +0800 Subject: [PATCH] =?UTF-8?q?=E5=88=86=E8=B4=A6=E5=89=8D=E6=9C=9F=E7=9A=84?= =?UTF-8?q?=E5=B7=A5=E4=BD=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../mall/common/feignService/ShopService.java | 20 ++ .../modules/lakala/LklOrderSeparate.java | 3 + .../common/modules/order/ShopOrderData.java | 3 + .../common/modules/order/ShopOrderLkl.java | 20 +- .../controller/mobile/IndexController.java | 6 +- .../mall/pay/service/LakalaPayService.java | 3 +- .../service/impl/LakalaPayServiceImpl.java | 15 +- .../impl/PayConsumeDepositServiceImpl.java | 2 +- .../service/impl/PayUserPayServiceImpl.java | 39 ++-- .../shop/lakala/service/LakalaApiService.java | 5 +- .../service/impl/LakalaApiServiceImpl.java | 75 ++++--- .../mobile/ShopOrderLklController.java | 39 ++++ .../order/listener/OrderPayedListener.java | 2 + .../order/service/ShopOrderDataService.java | 9 + .../order/service/ShopOrderLklService.java | 24 ++- .../impl/ShopOrderBaseServiceImpl.java | 33 +++ .../impl/ShopOrderDataServiceImpl.java | 30 +++ .../service/impl/ShopOrderLklServiceImpl.java | 190 +++++++++++++++++- .../store/service/ShopStoreBaseService.java | 1 + .../service/impl/ShopMchEntryServiceImpl.java | 75 ++++--- .../impl/ShopStoreBaseServiceImpl.java | 48 +++-- 21 files changed, 527 insertions(+), 115 deletions(-) create mode 100644 mall-shop/src/main/java/com/suisung/mall/shop/order/controller/mobile/ShopOrderLklController.java diff --git a/mall-common/src/main/java/com/suisung/mall/common/feignService/ShopService.java b/mall-common/src/main/java/com/suisung/mall/common/feignService/ShopService.java index 990b08a9..2e9c2bd1 100644 --- a/mall-common/src/main/java/com/suisung/mall/common/feignService/ShopService.java +++ b/mall-common/src/main/java/com/suisung/mall/common/feignService/ShopService.java @@ -1,5 +1,6 @@ package com.suisung.mall.common.feignService; +import cn.hutool.json.JSONObject; import com.suisung.mall.common.api.CommonResult; import com.suisung.mall.common.domain.OssDto; import com.suisung.mall.common.modules.base.ShopBaseDistrict; @@ -280,5 +281,24 @@ public interface ShopService { @PostMapping(value = "/mobile/shop/merch/approval/status") Long shopMerchEntryApprovalStatus(@RequestBody Map params); + + /** + * 当拉卡拉支付时,新增一个拉卡拉订单信息 + * + * @param lklPayReqAndRespJson 参数参考实现方法 + * @return + */ + @PostMapping(value = "/mobile/shop/orderlkl/pay/add/order") + Boolean lklPayAddShopOrderLkl(@RequestBody JSONObject lklPayReqAndRespJson); + + /** + * 当拉卡拉支付成功后,更改一个拉卡拉订单信息 + * + * @param lklPayNotifyDataJson 参数参考实现方法 + * @return + */ + @PostMapping(value = "/mobile/shop/orderlkl/pay/notify/update/order") + Boolean lklPayNotifyUpdateShopOrderLkl(@RequestBody JSONObject lklPayNotifyDataJson); + } diff --git a/mall-common/src/main/java/com/suisung/mall/common/modules/lakala/LklOrderSeparate.java b/mall-common/src/main/java/com/suisung/mall/common/modules/lakala/LklOrderSeparate.java index bd3ef01c..568e852c 100644 --- a/mall-common/src/main/java/com/suisung/mall/common/modules/lakala/LklOrderSeparate.java +++ b/mall-common/src/main/java/com/suisung/mall/common/modules/lakala/LklOrderSeparate.java @@ -76,6 +76,9 @@ public class LklOrderSeparate { @ApiModelProperty(value = "最终分账明细,JSON 格式") private String detail_datas; + @ApiModelProperty(value = "总计分账金额") + private Integer total_separate_value; + @ApiModelProperty(value = "拉卡拉机构编号") private String lkl_org_no; diff --git a/mall-common/src/main/java/com/suisung/mall/common/modules/order/ShopOrderData.java b/mall-common/src/main/java/com/suisung/mall/common/modules/order/ShopOrderData.java index 3ad82ab4..9121be53 100644 --- a/mall-common/src/main/java/com/suisung/mall/common/modules/order/ShopOrderData.java +++ b/mall-common/src/main/java/com/suisung/mall/common/modules/order/ShopOrderData.java @@ -92,6 +92,9 @@ public class ShopOrderData implements Serializable { @ApiModelProperty(value = "实际运费金额-卖家可修改") private BigDecimal order_shipping_fee; + @ApiModelProperty(value = "总计分账金额(从拉卡拉上分账,分给平台和代理商费用),单位:元") + private BigDecimal total_separate_value; + @ApiModelProperty(value = "平台费(分给平台或代理商的费用),根据不同的店铺分类,从商品原价中扣除相应的费用。") private BigDecimal platform_fee; diff --git a/mall-common/src/main/java/com/suisung/mall/common/modules/order/ShopOrderLkl.java b/mall-common/src/main/java/com/suisung/mall/common/modules/order/ShopOrderLkl.java index b147537a..efba36be 100644 --- a/mall-common/src/main/java/com/suisung/mall/common/modules/order/ShopOrderLkl.java +++ b/mall-common/src/main/java/com/suisung/mall/common/modules/order/ShopOrderLkl.java @@ -38,12 +38,6 @@ public class ShopOrderLkl implements Serializable { private String order_id; - private String log_no; - - private String log_date; - - private String merchant_no; - private Integer total_amt; private Integer shopping_fee; @@ -56,12 +50,26 @@ public class ShopOrderLkl implements Serializable { private String trans_type; + private String trade_status; + + private String lkl_log_no; + + private String lkl_log_date; + private String lkl_trade_no; + private String lkl_merchant_no; + private String lkl_term_no; + private String notify_url; + + private String lkl_req; + private String lkl_resp; + private String lkl_notify_resp; + private Integer status; private Date created_at; diff --git a/mall-pay/src/main/java/com/suisung/mall/pay/controller/mobile/IndexController.java b/mall-pay/src/main/java/com/suisung/mall/pay/controller/mobile/IndexController.java index 1b2287be..415a07ff 100644 --- a/mall-pay/src/main/java/com/suisung/mall/pay/controller/mobile/IndexController.java +++ b/mall-pay/src/main/java/com/suisung/mall/pay/controller/mobile/IndexController.java @@ -63,8 +63,8 @@ public class IndexController extends BaseControllerImpl { @ApiOperation(value = "测试接口", notes = "测试接口") @RequestMapping(value = "/test/case", method = RequestMethod.POST) public JSONObject testCase(HttpServletRequest request, HttpServletResponse response, - @RequestBody JSONObject objectJSON){ - return lakalaPayService.transPreOrder(request,response, (String) objectJSON.get("orderId")); + @RequestBody JSONObject objectJSON) { + return lakalaPayService.transPreOrder(request, response, (String) objectJSON.get("orderId")); } @ApiOperation(value = "获取支付密码", notes = "获取支付密码") @@ -243,7 +243,7 @@ public class IndexController extends BaseControllerImpl { return payUserPayService.notifyUrl(request, response, "wx_native"); } - @ApiOperation(value = "拉卡拉在微信回调通知", notes = "拉卡拉在微信回调通知") + @ApiOperation(value = "第三方拉卡拉在微信回调通知", notes = "第三方拉卡拉在微信回调通知") @RequestMapping(value = "/lkl_wxPay_notify_url", method = RequestMethod.POST) public String lklWxNotifyUrl(HttpServletRequest request) { return payUserPayService.lklNotifyUrl(request); diff --git a/mall-pay/src/main/java/com/suisung/mall/pay/service/LakalaPayService.java b/mall-pay/src/main/java/com/suisung/mall/pay/service/LakalaPayService.java index 738bc79c..55050b64 100644 --- a/mall-pay/src/main/java/com/suisung/mall/pay/service/LakalaPayService.java +++ b/mall-pay/src/main/java/com/suisung/mall/pay/service/LakalaPayService.java @@ -28,6 +28,7 @@ public interface LakalaPayService { * @param termNo 终端号 * @param xcxAppId 小程序appid * @param openId openid + * @param storeId 店铺号 * @param orderId 订单号 * @param subject 订单标题 * @param totalAmount 订单金额 @@ -36,7 +37,7 @@ public interface LakalaPayService { * @param remark 备注 * @return */ - JSONObject transPreOrder(String merchantNo, String termNo, String xcxAppId, String openId, String orderId, String subject, String totalAmount, String notifyURL, String requestIP, String remark); + JSONObject transPreOrder(String merchantNo, String termNo, String xcxAppId, String openId, String storeId, String orderId, String subject, String totalAmount, String notifyURL, String requestIP, String remark); /** * 聚合扫码-交易查询 diff --git a/mall-pay/src/main/java/com/suisung/mall/pay/service/impl/LakalaPayServiceImpl.java b/mall-pay/src/main/java/com/suisung/mall/pay/service/impl/LakalaPayServiceImpl.java index b553420a..6805dae1 100644 --- a/mall-pay/src/main/java/com/suisung/mall/pay/service/impl/LakalaPayServiceImpl.java +++ b/mall-pay/src/main/java/com/suisung/mall/pay/service/impl/LakalaPayServiceImpl.java @@ -157,6 +157,7 @@ public class LakalaPayServiceImpl implements LakalaPayService { * @param termNo 终端号 * @param xcxAppId 小程序appid * @param openId openid + * @param storeId 订单号 * @param orderId 订单号 * @param subject 订单标题 * @param totalAmount 订单金额 @@ -166,7 +167,7 @@ public class LakalaPayServiceImpl implements LakalaPayService { * @return */ @Override - public JSONObject transPreOrder(String merchantNo, String termNo, String xcxAppId, String openId, String orderId, String subject, String totalAmount, String notifyURL, String requestIP, String remark) { + public JSONObject transPreOrder(String merchantNo, String termNo, String xcxAppId, String openId, String storeId, String orderId, String subject, String totalAmount, String notifyURL, String requestIP, String remark) { // 1. 配置初始化 initLKLSDK(); @@ -188,7 +189,7 @@ public class LakalaPayServiceImpl implements LakalaPayService { v3LabsTransPreorderWechatReq.setAccountType("WECHAT"); // 41:NATIVE((ALIPAY,云闪付支持,京东白条分期)51:JSAPI(微信公众号支付,支付宝服务窗支付,银联JS支付,翼支付JS支付、拉卡拉钱包支付)71:微信小程序支付 61:APP支付(微信APP支付) v3LabsTransPreorderWechatReq.setTransType("51"); - v3LabsTransPreorderWechatReq.setTotalAmount(totalAmount); + v3LabsTransPreorderWechatReq.setTotalAmount(totalAmount); // 应支付金额,单位:分 v3LabsTransPreorderWechatReq.setSettleType("1"); //“0”或者空,常规结算方式,如需接拉卡拉分账通需传“1”,商户未开通分账之前切记不用上送此参数。; v3LabsTransPreorderWechatReq.setNotifyUrl(notifyURL); v3LabsTransPreorderWechatReq.setRemark(remark); @@ -202,6 +203,7 @@ public class LakalaPayServiceImpl implements LakalaPayService { wechatBus.setSubAppid(xcxAppId); // 小程序appId wechatBus.setUserId(openId); // 微信 openId wechatBus.setDeviceInfo("WEB"); // 终端设备号(门店号或收银设备ID),注意:PC网页或JSAPI支付请传”WEB” + wechatBus.setAttach(storeId); // 附加数据,商户自定义数据,在查询交易结果时原样返回。 v3LabsTransPreorderWechatReq.setAccBusiFields(wechatBus); try { @@ -216,8 +218,13 @@ public class LakalaPayServiceImpl implements LakalaPayService { JSONObject lakalaRespJSON = JSONUtil.parseObj(responseStr); - // || !lakalaRespJSON.getStr("code").equals("BBS00000") - + if (lakalaRespJSON != null && lakalaRespJSON.getStr("code").equals("BBS00000")) { + // 新增一个拉卡拉订单记录 shop_order_lkl 表 + JSONObject lklPayReqAndRespJson = new JSONObject(); + lklPayReqAndRespJson.put("req", JSONUtil.parseObj(v3LabsTransPreorderWechatReq)); + lklPayReqAndRespJson.put("resp", lakalaRespJSON); + shopService.lklPayAddShopOrderLkl(lklPayReqAndRespJson); + } //4. 响应 return lakalaRespJSON; } catch (SDKException e) { diff --git a/mall-pay/src/main/java/com/suisung/mall/pay/service/impl/PayConsumeDepositServiceImpl.java b/mall-pay/src/main/java/com/suisung/mall/pay/service/impl/PayConsumeDepositServiceImpl.java index 84529a1b..b845cb23 100644 --- a/mall-pay/src/main/java/com/suisung/mall/pay/service/impl/PayConsumeDepositServiceImpl.java +++ b/mall-pay/src/main/java/com/suisung/mall/pay/service/impl/PayConsumeDepositServiceImpl.java @@ -573,7 +573,7 @@ public class PayConsumeDepositServiceImpl extends BaseServiceImpl authMap = LakalaUtil.getLakalaAuthorizationMap(authorization); @@ -1296,9 +1298,14 @@ public class PayUserPayServiceImpl extends BaseServiceImpl tradeQueryWrapper = new QueryWrapper<>(); - tradeQueryWrapper.eq("order_id", order_id); + tradeQueryWrapper.eq("order_id", orderId); PayConsumeTrade trade_row_tmp = payConsumeTradeService.findOne(tradeQueryWrapper); Integer payment_store_id = trade_row_tmp != null ? trade_row_tmp.getStore_id() : 0; @@ -1318,7 +1325,7 @@ public class PayUserPayServiceImpl extends BaseServiceImpl innerDoOrderSeparate(String orderId); + Pair innerDoOrderSeparate(String orderId, String storeId); /** * 分账结果通知 diff --git a/mall-shop/src/main/java/com/suisung/mall/shop/lakala/service/impl/LakalaApiServiceImpl.java b/mall-shop/src/main/java/com/suisung/mall/shop/lakala/service/impl/LakalaApiServiceImpl.java index 9c6d4e52..e0dcd8ce 100644 --- a/mall-shop/src/main/java/com/suisung/mall/shop/lakala/service/impl/LakalaApiServiceImpl.java +++ b/mall-shop/src/main/java/com/suisung/mall/shop/lakala/service/impl/LakalaApiServiceImpl.java @@ -1625,29 +1625,31 @@ public class LakalaApiServiceImpl implements LakalaApiService { * @return */ @Override - public Pair innerDoOrderSeparate(String orderId) { + public Pair innerDoOrderSeparate(String orderId, String storeId) { // 输入参数校验 if (StrUtil.isBlank(orderId)) { return Pair.of(false, "订单号不能为空"); } try { + // TODO 检查可分账余额是否足够? + // 初始化拉卡拉SDK initLKLSDK(); // 查询订单信息 - List shopOrders = shopOrderLklService.selectByOrderId(orderId, ""); - if (CollectionUtil.isEmpty(shopOrders)) { + List shopOrderLklList = shopOrderLklService.selectByOrderId(orderId, "", storeId); + if (CollectionUtil.isEmpty(shopOrderLklList)) { return Pair.of(false, "订单不存在"); } - int totalCount = shopOrders.size(); + int totalCount = shopOrderLklList.size(); int successCount = 0; StringBuilder errorMessages = new StringBuilder(); // 遍历处理每个店铺订单的分账 - for (ShopOrderLkl order : shopOrders) { - String merchantNo = order.getMerchant_no(); + for (ShopOrderLkl order : shopOrderLklList) { + String merchantNo = order.getLkl_merchant_no(); Integer paymentAmount = order.getTotal_amt(); Integer shoppingFee = order.getShopping_fee(); BigDecimal splitRatioMch = order.getSplit_ratio(); @@ -1680,8 +1682,8 @@ public class LakalaApiServiceImpl implements LakalaApiService { // 构建分账请求对象 V3SacsSeparateRequest request = new V3SacsSeparateRequest(); request.setMerchantNo(merchantNo); - request.setLogNo(order.getLog_no()); - request.setLogDate(order.getLog_date()); + request.setLogNo(order.getLkl_log_no()); + request.setLogDate(order.getLkl_log_date()); request.setOutSeparateNo(orderId); request.setTotalAmt(paymentAmount.toString()); request.setLklOrgNo(orgCode); @@ -1699,8 +1701,10 @@ public class LakalaApiServiceImpl implements LakalaApiService { recvDatas.add(receiver); } + Integer totalSeparateValue = 0;// 平台方和代理商总计分账金额 // 2. 再处理剩余金额的分账(如果可以分账) if (canSplit) { + // 计算实际可分账金额(扣除运费后) Integer splitAmount = paymentAmount - shoppingFee; // 计算平台+代理商的总比例 @@ -1715,6 +1719,8 @@ public class LakalaApiServiceImpl implements LakalaApiService { receiver.setRecvNo(platform.getReceiver_no()); receiver.setSeparateValue(platformValue.toString()); recvDatas.add(receiver); + + totalSeparateValue += platformValue.intValue(); } // 代理商分账(扣除平台1%后的剩余比例) @@ -1725,6 +1731,8 @@ public class LakalaApiServiceImpl implements LakalaApiService { receiver.setRecvNo(distributors.get(0).getReceiver_no()); receiver.setSeparateValue(distributorValue.toString()); recvDatas.add(receiver); + + totalSeparateValue += distributorValue.intValue(); } } else { // 仅平台分账模式 @@ -1735,6 +1743,8 @@ public class LakalaApiServiceImpl implements LakalaApiService { receiver.setRecvNo(platform.getReceiver_no()); receiver.setSeparateValue(platformValue.toString()); recvDatas.add(receiver); + + totalSeparateValue += platformValue.intValue(); } } } @@ -1762,21 +1772,22 @@ public class LakalaApiServiceImpl implements LakalaApiService { // 保存分账记录 JSONObject respData = respJson.getJSONObject("resp_data"); - LklOrderSeparate record = new LklOrderSeparate(); - record.setSeparate_no(respData.getStr("separate_no")); - record.setOut_separate_no(request.getOutSeparateNo()); - record.setMerchant_no(merchantNo); - record.setLog_no(request.getLogNo()); - record.setLog_date(request.getLogDate()); - record.setOrder_id(order.getOrder_id()); - record.setTotal_amt(request.getTotalAmt()); - record.setNotify_url(request.getNotifyUrl()); - record.setLkl_org_no(request.getLklOrgNo()); - record.setRecv_datas(JSONUtil.toJsonStr(request.getRecvDatas())); - record.setStatus(respData.getStr("status")); + LklOrderSeparate lklOrderSeparate = new LklOrderSeparate(); + lklOrderSeparate.setSeparate_no(respData.getStr("separate_no")); + lklOrderSeparate.setOut_separate_no(request.getOutSeparateNo()); + lklOrderSeparate.setMerchant_no(merchantNo); + lklOrderSeparate.setLog_no(request.getLogNo()); + lklOrderSeparate.setLog_date(request.getLogDate()); + lklOrderSeparate.setOrder_id(order.getOrder_id()); + lklOrderSeparate.setTotal_amt(request.getTotalAmt()); + lklOrderSeparate.setNotify_url(request.getNotifyUrl()); + lklOrderSeparate.setLkl_org_no(request.getLklOrgNo()); + lklOrderSeparate.setRecv_datas(JSONUtil.toJsonStr(request.getRecvDatas())); + lklOrderSeparate.setStatus(respData.getStr("status")); + lklOrderSeparate.setTotal_separate_value(totalSeparateValue); try { - lklOrderSeparateService.addOrUpdateByReceiverNo(record); + lklOrderSeparateService.addOrUpdateByReceiverNo(lklOrderSeparate); successCount++; } catch (Exception e) { log.error("保存分账记录失败: {}", e.getMessage(), e); @@ -1848,23 +1859,23 @@ public class LakalaApiServiceImpl implements LakalaApiService { } // 4. 构建分账记录对象 - LklOrderSeparate record = new LklOrderSeparate(); - record.setLog_no(logNo); - record.setSeparate_no(separateNo); - record.setOut_separate_no(outSeparateNo); - record.setStatus(status); - record.setFinal_status(finalStatus); - record.setCal_type(paramsJson.getStr("cal_type")); - record.setSeparate_type(paramsJson.getStr("separate_type")); - record.setSeparate_date(paramsJson.getStr("separate_date")); + LklOrderSeparate lklOrderSeparate = new LklOrderSeparate(); + lklOrderSeparate.setLog_no(logNo); + lklOrderSeparate.setSeparate_no(separateNo); + lklOrderSeparate.setOut_separate_no(outSeparateNo); + lklOrderSeparate.setStatus(status); + lklOrderSeparate.setFinal_status(finalStatus); + lklOrderSeparate.setCal_type(paramsJson.getStr("cal_type")); + lklOrderSeparate.setSeparate_type(paramsJson.getStr("separate_type")); + lklOrderSeparate.setSeparate_date(paramsJson.getStr("separate_date")); // 处理detail_datas(避免空指针) JSONArray detailDatas = paramsJson.getJSONArray("detail_datas"); - record.setDetail_datas(detailDatas != null ? detailDatas.toString() : "[]"); + lklOrderSeparate.setDetail_datas(detailDatas != null ? detailDatas.toString() : "[]"); // 5. 持久化处理 try { - boolean updateSuccess = lklOrderSeparateService.addOrUpdateByReceiverNo(record); + boolean updateSuccess = lklOrderSeparateService.addOrUpdateByReceiverNo(lklOrderSeparate); if (!updateSuccess) { log.error("分账记录更新失败, separateNo={}", separateNo); return JSONUtil.createObj() diff --git a/mall-shop/src/main/java/com/suisung/mall/shop/order/controller/mobile/ShopOrderLklController.java b/mall-shop/src/main/java/com/suisung/mall/shop/order/controller/mobile/ShopOrderLklController.java new file mode 100644 index 00000000..17983a29 --- /dev/null +++ b/mall-shop/src/main/java/com/suisung/mall/shop/order/controller/mobile/ShopOrderLklController.java @@ -0,0 +1,39 @@ +package com.suisung.mall.shop.order.controller.mobile; + +import cn.hutool.json.JSONObject; +import com.suisung.mall.common.service.impl.BaseControllerImpl; +import com.suisung.mall.shop.order.service.ShopOrderLklService; +import io.swagger.annotations.Api; +import io.swagger.annotations.ApiOperation; +import org.springframework.web.bind.annotation.RequestBody; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RestController; + +import javax.annotation.Resource; + +/** + * 拉卡拉订单控制器 + */ +@Api(tags = "拉卡拉订单控制器,拉卡拉支付时和成功之后,写入拉卡拉的订单信息。") +@RestController() +@RequestMapping("/mobile/shop/orderlkl") +public class ShopOrderLklController extends BaseControllerImpl { + + @Resource + private ShopOrderLklService shopOrderLklService; + + @ApiOperation(value = "当拉卡拉支付时,新增一个拉卡拉订单信息", notes = "当拉卡拉支付时,新增一个拉卡拉订单信息") + @RequestMapping(value = "/pay/add/order", method = RequestMethod.POST) + public Boolean lklPayAddShopOrderLkl(@RequestBody JSONObject lklPayReqAndRespJson) { + return shopOrderLklService.addOrUpdateByLklPayDataJson(lklPayReqAndRespJson); + } + + @ApiOperation(value = "当拉卡拉支付成功后,更改一个拉卡拉订单信息", notes = "当拉卡拉支付成功后,更改一个拉卡拉订单信息") + @RequestMapping(value = "/pay/notify/update/order", method = RequestMethod.POST) + public Boolean lklPayNotifyUpdateShopOrderLkl(@RequestBody JSONObject lklPayNotifyDataJson) { + return shopOrderLklService.addOrUpdateByLklPayNotifyDataJson(lklPayNotifyDataJson); + } + +} + diff --git a/mall-shop/src/main/java/com/suisung/mall/shop/order/listener/OrderPayedListener.java b/mall-shop/src/main/java/com/suisung/mall/shop/order/listener/OrderPayedListener.java index eb378b64..0e358008 100644 --- a/mall-shop/src/main/java/com/suisung/mall/shop/order/listener/OrderPayedListener.java +++ b/mall-shop/src/main/java/com/suisung/mall/shop/order/listener/OrderPayedListener.java @@ -25,6 +25,8 @@ import java.util.List; /** * 支付成功后,微信和支付宝发出异步通知消息到 RabbitMQ, * 这里 MQ 监听到消息后执行更改订单状态为:已支付。 + *

+ * payConsumeDepositService.processDeposit 这个方法里发出 mq 消息 */ @Service @Slf4j diff --git a/mall-shop/src/main/java/com/suisung/mall/shop/order/service/ShopOrderDataService.java b/mall-shop/src/main/java/com/suisung/mall/shop/order/service/ShopOrderDataService.java index 0886be3d..ead18f6d 100644 --- a/mall-shop/src/main/java/com/suisung/mall/shop/order/service/ShopOrderDataService.java +++ b/mall-shop/src/main/java/com/suisung/mall/shop/order/service/ShopOrderDataService.java @@ -3,6 +3,8 @@ package com.suisung.mall.shop.order.service; import com.suisung.mall.common.modules.order.ShopOrderData; import com.suisung.mall.core.web.service.IBaseService; +import java.math.BigDecimal; + /** *

* 订单详细信息 服务类 @@ -13,4 +15,11 @@ import com.suisung.mall.core.web.service.IBaseService; */ public interface ShopOrderDataService extends IBaseService { + /** + * 获取订单运费 + * + * @param orderId + * @return + */ + BigDecimal getOrderShippingFee(String orderId); } diff --git a/mall-shop/src/main/java/com/suisung/mall/shop/order/service/ShopOrderLklService.java b/mall-shop/src/main/java/com/suisung/mall/shop/order/service/ShopOrderLklService.java index 1e4c12ef..906360ed 100644 --- a/mall-shop/src/main/java/com/suisung/mall/shop/order/service/ShopOrderLklService.java +++ b/mall-shop/src/main/java/com/suisung/mall/shop/order/service/ShopOrderLklService.java @@ -8,6 +8,7 @@ package com.suisung.mall.shop.order.service; +import cn.hutool.json.JSONObject; import com.suisung.mall.common.modules.order.ShopOrderLkl; import com.suisung.mall.core.web.service.IBaseService; @@ -23,12 +24,33 @@ public interface ShopOrderLklService extends IBaseService { */ Boolean addOrUpdateByStoreOrder(ShopOrderLkl record); + /** + * 根据拉卡拉的支付请求和响应数据,新增或更新拉卡拉的订单信息 + * + * @param lklPayReqAndRespJson 拉卡拉支付请求和响应JSON参数 + * @return + */ + Boolean addOrUpdateByLklPayDataJson(JSONObject lklPayReqAndRespJson); + + /** + * 根据拉卡拉的回调数据,更新拉卡拉的订单信息 + * + * @param lklPayNotifyDataJson 异步通知返回的body json数据: + * // {"out_trade_no":"202203151637334864280014","trade_no":"2022031566210203291925","log_no":"66210203291925", + * // "acc_trade_no":"2022031522001483661454130929 ","trade_status":"SUCCESS","trade_state":"SUCCESS","total_amount":"1", + * // "payer_amount":"1","acc_settle_amount":"1","trade_time":"20220315163808","user_id1":"app***@163.com", + * // "user_id2":"2088432881453660","notify_url":"https://www.baidu.com","account_type":"ALIPAY","card_type":"99"} + * @return + */ + Boolean addOrUpdateByLklPayNotifyDataJson(JSONObject lklPayNotifyDataJson); + /** * 根据订单编号查询多条记录(因为一个订单里可能有多个店铺的商品) * * @param orderId + * @param lklLogNo 拉卡拉支付流水号,可选参数 * @param storeId * @return */ - List selectByOrderId(String orderId, String storeId); + List selectByOrderId(String orderId, String lklLogNo, String storeId); } diff --git a/mall-shop/src/main/java/com/suisung/mall/shop/order/service/impl/ShopOrderBaseServiceImpl.java b/mall-shop/src/main/java/com/suisung/mall/shop/order/service/impl/ShopOrderBaseServiceImpl.java index ca31d97f..25706c8d 100644 --- a/mall-shop/src/main/java/com/suisung/mall/shop/order/service/impl/ShopOrderBaseServiceImpl.java +++ b/mall-shop/src/main/java/com/suisung/mall/shop/order/service/impl/ShopOrderBaseServiceImpl.java @@ -6211,6 +6211,7 @@ public class ShopOrderBaseServiceImpl extends BaseServiceImpl @@ -17,4 +19,32 @@ import org.springframework.stereotype.Service; */ @Service public class ShopOrderDataServiceImpl extends BaseServiceImpl implements ShopOrderDataService { + /** + * 获取订单运费 + * + * @param orderId + * @return + */ + @Override + public BigDecimal getOrderShippingFee(String orderId) { + if (orderId == null) { + return BigDecimal.ZERO; + } + + ShopOrderData shopOrderData = getById(orderId); + if (shopOrderData == null) { + return BigDecimal.ZERO; + } + + BigDecimal result = shopOrderData.getOrder_shipping_fee(); + if (result == null || result.compareTo(BigDecimal.ZERO) == -1) { + result = shopOrderData.getOrder_shipping_fee_amount(); + } + + if (result == null || result.compareTo(BigDecimal.ZERO) == -1) { + return BigDecimal.ZERO; + } + + return result; + } } diff --git a/mall-shop/src/main/java/com/suisung/mall/shop/order/service/impl/ShopOrderLklServiceImpl.java b/mall-shop/src/main/java/com/suisung/mall/shop/order/service/impl/ShopOrderLklServiceImpl.java index acb44ac6..f3719cee 100644 --- a/mall-shop/src/main/java/com/suisung/mall/shop/order/service/impl/ShopOrderLklServiceImpl.java +++ b/mall-shop/src/main/java/com/suisung/mall/shop/order/service/impl/ShopOrderLklServiceImpl.java @@ -9,30 +9,48 @@ package com.suisung.mall.shop.order.service.impl; import cn.hutool.core.collection.CollectionUtil; +import cn.hutool.core.convert.Convert; import cn.hutool.core.util.StrUtil; +import cn.hutool.json.JSONObject; +import cn.hutool.json.JSONUtil; import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; import com.suisung.mall.common.modules.order.ShopOrderLkl; +import com.suisung.mall.common.utils.DateTimeUtils; import com.suisung.mall.core.web.service.impl.BaseServiceImpl; import com.suisung.mall.shop.order.mapper.ShopOrderLklMapper; +import com.suisung.mall.shop.order.service.ShopOrderDataService; import com.suisung.mall.shop.order.service.ShopOrderLklService; +import com.suisung.mall.shop.store.service.ShopStoreBaseService; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang3.StringUtils; +import org.springframework.context.annotation.Lazy; import org.springframework.stereotype.Service; +import javax.annotation.Resource; +import java.math.BigDecimal; +import java.time.LocalDateTime; import java.util.List; @Slf4j @Service public class ShopOrderLklServiceImpl extends BaseServiceImpl implements ShopOrderLklService { + @Lazy + @Resource + private ShopStoreBaseService shopStoreBaseService; + + @Lazy + @Resource + private ShopOrderDataService shopOrderDataService; + @Override public Boolean addOrUpdateByStoreOrder(ShopOrderLkl record) { if (record == null - || StringUtils.isAnyBlank(record.getOrder_id(), record.getStore_id(), record.getLog_no())) { + || StringUtils.isAnyBlank(record.getOrder_id(), record.getLkl_log_no())) { return false; } - List existsRecordList = selectByOrderId(record.getOrder_id(), record.getStore_id()); + List existsRecordList = selectByOrderId(record.getOrder_id(), record.getLkl_log_no(), record.getStore_id()); if (CollectionUtil.isNotEmpty(existsRecordList) && existsRecordList.get(0) != null && existsRecordList.get(0).getId() > 0) { @@ -45,19 +63,181 @@ public class ShopOrderLklServiceImpl extends BaseServiceImpl selectByOrderId(String orderId, String storeId) { + public Boolean addOrUpdateByLklPayDataJson(JSONObject lklPayReqAndRespJson) { + if (lklPayReqAndRespJson == null) { + log.warn("参数为空,无法保存拉卡拉订单记录"); + return false; + } + + // 获取请求体和响应体 + JSONObject reqDataJson = JSONUtil.parseObj(lklPayReqAndRespJson.getByPath("req.req_data")); + JSONObject respDataJson = JSONUtil.parseObj(lklPayReqAndRespJson.getByPath("resp.resp_data")); + + if (reqDataJson == null || respDataJson == null) { + log.warn("请求或响应数据中的 req_data / resp_data 为空"); + return false; + } + + // 提取订单号并校验 + String orderId = reqDataJson.getStr("out_trade_no"); + if (StringUtils.isBlank(orderId)) { + log.warn("订单ID为空,无法保存拉卡拉支付记录"); + return false; + } + + ShopOrderLkl record = new ShopOrderLkl(); + record.setOrder_id(orderId); + + // 设置请求内容 + record.setLkl_merchant_no(reqDataJson.getStr("merchant_no")); + record.setLkl_term_no(reqDataJson.getStr("term_no")); + + // 订单金额安全处理 + Integer amount = reqDataJson.getInt("total_amount"); + if (amount == null) { + log.error("订单{}金额无效: {}", orderId, amount); + return false; + } + record.setTotal_amt(amount); + + record.setAccount_type(reqDataJson.getStr("account_type")); + record.setTrans_type(reqDataJson.getStr("trans_type")); + record.setNotify_url(reqDataJson.getStr("notify_url")); + + + record.setLkl_req(JSONUtil.toJsonStr(reqDataJson)); + + // 设置响应内容 + record.setLkl_log_no(respDataJson.getStr("log_no")); + record.setLkl_trade_no(respDataJson.getStr("trade_no")); + record.setLkl_resp(JSONUtil.toJsonStr(respDataJson)); + + // 关键数据:获取店铺ID,分账比例用到 + Integer storeId = 0; + Object attachObj = reqDataJson.getByPath("acc_busi_fields.attach"); + if (attachObj != null) { + storeId = Convert.toInt(attachObj); + record.setStore_id(storeId.toString()); + } + + // 运费和商家分账比例 + BigDecimal shipperFee = shopOrderDataService.getOrderShippingFee(orderId); + record.setShopping_fee(shipperFee.multiply(BigDecimal.valueOf(100)).intValue()); // 运费,单位:分 + record.setSplit_ratio(shopStoreBaseService.getStorePlatformRatio(storeId, false)); // 商家分账比例 + + return addOrUpdateByStoreOrder(record); + } + + @Override + public Boolean addOrUpdateByLklPayNotifyDataJson(JSONObject lklPayNotifyDataJson) { + if (lklPayNotifyDataJson == null) { + log.warn("参数为空,无法保存拉卡拉支付通知记录"); + return false; + } + + String orderId = lklPayNotifyDataJson.getStr("out_trade_no"); + if (StringUtils.isBlank(orderId)) { + log.warn("订单ID为空,无法保存拉卡拉支付通知记录"); + return false; + } + + ShopOrderLkl record = new ShopOrderLkl(); + record.setOrder_id(orderId); + + // 设置必填字段并校验 + String logNo = lklPayNotifyDataJson.getStr("log_no"); + if (StringUtils.isBlank(logNo)) { + log.warn("log_no 为空,无法保存拉卡拉支付通知记录"); + return false; + } + record.setLkl_log_no(logNo); + + // 设置日期字段 + record.setLkl_log_date(DateTimeUtils.formatDateTime(LocalDateTime.now(), "yyyy-MM-dd")); + + // 设置可选字段 + record.setLkl_trade_no(lklPayNotifyDataJson.getStr("trade_no")); + record.setTrade_status(lklPayNotifyDataJson.getStr("trade_status")); + + // 安全地设置响应内容 + record.setLkl_resp(JSONUtil.toJsonStr(lklPayNotifyDataJson)); + + return addOrUpdateByStoreOrder(record); + } + + /** + * 根据订单编号查询多条记录(因为一个订单里可能有多个店铺的商品) + * + * @param orderId 订单Id,必填参数 + * @param lklLogNo 拉卡拉支付流水号,可选参数 + * @param storeId 店铺Id,可选参数 + * @return + */ + @Override + public List selectByOrderId(String orderId, String lklLogNo, String storeId) { if (StringUtils.isBlank(orderId)) { return null; } QueryWrapper queryWrapper = new QueryWrapper<>(); queryWrapper.eq("order_id", orderId).orderByAsc("id"); + + if (StrUtil.isNotBlank(lklLogNo)) { + queryWrapper.eq("lkl_log_no", lklLogNo); + } + if (StrUtil.isNotBlank(storeId)) { queryWrapper.eq("store_id", storeId); } diff --git a/mall-shop/src/main/java/com/suisung/mall/shop/store/service/ShopStoreBaseService.java b/mall-shop/src/main/java/com/suisung/mall/shop/store/service/ShopStoreBaseService.java index a62579ff..04a690f1 100644 --- a/mall-shop/src/main/java/com/suisung/mall/shop/store/service/ShopStoreBaseService.java +++ b/mall-shop/src/main/java/com/suisung/mall/shop/store/service/ShopStoreBaseService.java @@ -172,4 +172,5 @@ public interface ShopStoreBaseService extends IBaseService { * @return 平台分账比例的数值 */ BigDecimal getStorePlatformRatio(Integer storeId, boolean reCalculate); + } diff --git a/mall-shop/src/main/java/com/suisung/mall/shop/store/service/impl/ShopMchEntryServiceImpl.java b/mall-shop/src/main/java/com/suisung/mall/shop/store/service/impl/ShopMchEntryServiceImpl.java index 472384b9..3c25245d 100644 --- a/mall-shop/src/main/java/com/suisung/mall/shop/store/service/impl/ShopMchEntryServiceImpl.java +++ b/mall-shop/src/main/java/com/suisung/mall/shop/store/service/impl/ShopMchEntryServiceImpl.java @@ -43,6 +43,7 @@ import org.springframework.data.util.Pair; import org.springframework.stereotype.Service; import javax.annotation.Resource; +import java.math.BigDecimal; import java.util.*; /** @@ -497,58 +498,73 @@ public class ShopMchEntryServiceImpl extends BaseServiceImpl updateWrapper = new UpdateWrapper<>(); - if (approvalStatus.equals(CommonConstant.MCH_APPR_STA_LKL_PADDING) && StrUtil.isBlank(approvalRemark)) { - // 审核通过 - approvalRemark = "初步审核通过,等待进一步审核。";//"审核通过,后续将向您发起签署电子合同流程。"; - updateWrapper.set("signed_status", CommonConstant.CONTRACT_SIGN_STA_ING); - updateWrapper.set("approval_status", CommonConstant.MCH_APPR_STA_LKL_PADDING); // 进入拉卡拉审核中 + updateWrapper.eq("id", id); - log.info("准备提交给拉卡拉进件审核。"); - } else if (approvalStatus.equals(CommonConstant.MCH_APPR_STA_NOPASS) && StrUtil.isBlank(approvalRemark)) { + // 设置默认审批备注 + if (StrUtil.isBlank(approvalRemark)) { approvalRemark = "审核未通过,请继续完善入驻资料信息。"; } - // 重要备注:自动计算商家分成比例 - record.setSplit_ratio(shopBaseStoreCategoryService.getStoreCategoryRatio(record.getBiz_category())); - - updateWrapper.eq("id", id) - .set("approval_status", approvalStatus) - .set("approval_remark", approvalRemark) - .set("updated_by", userId); - - // 指定哪些字段无效字段的审批细节 - if (StrUtil.isNotBlank(approvalInvalidCol)) { - updateWrapper.set("approval_invalid_col", approvalInvalidCol); + if (approvalStatus.equals(CommonConstant.MCH_APPR_STA_LKL_PADDING)) { + approvalRemark = "初审通过,等待进一步审核。"; + // updateWrapper.set("signed_status", CommonConstant.CONTRACT_SIGN_STA_ING); // 合同签署中 + approvalInvalidCol = "[]"; } + // 设置无效字段 + if (StrUtil.isBlank(approvalInvalidCol)) { + approvalInvalidCol = "[]"; + } + + + // 自动计算商家分成比例 + BigDecimal splitRatio = shopBaseStoreCategoryService.getStoreCategoryRatio(record.getBiz_category()); + if (splitRatio == null || splitRatio.compareTo(BigDecimal.ZERO) <= 0) { + splitRatio = new BigDecimal("100"); + } + + // 构建更新参数 + updateWrapper + .set("approval_status", approvalStatus) + .set("approval_remark", approvalRemark) + .set("split_ratio", splitRatio) + .set("approval_invalid_col", approvalInvalidCol) + .set("updated_by", userId); + + // 执行更新操作 if (!update(updateWrapper)) { + log.error("系统处理审批出错,请联系管理员!当前记录ID: {}", id); return CommonResult.failed("系统处理审批出错,请联系管理员!"); } + // 如果是驳回状态,直接返回成功消息 if (approvalStatus.equals(CommonConstant.MCH_APPR_STA_NOPASS)) { return CommonResult.success(null, "驳回成功!"); } @@ -557,11 +573,15 @@ public class ShopMchEntryServiceImpl extends BaseServiceImpl resultPair = lakalaApiService.applyLedgerMerEc(record.getLogin_mobile()); - if (!resultPair.getFirst()) { - return CommonResult.failed(resultPair.getSecond()); - } + try { + Pair resultPair = lakalaApiService.applyLedgerMerEc(record.getLogin_mobile()); + if (!resultPair.getFirst()) { + log.warn("拉卡拉电子合同签署申请失败: {}", resultPair.getSecond()); + return CommonResult.failed(resultPair.getSecond()); + } + +// E签宝暂时停止使用 // if (approvalStatus.equals(CommonConstant.Enable)) { // // 多线程执行电子合同生成和填充 // taskService.executeTask(() -> { @@ -576,6 +596,11 @@ public class ShopMchEntryServiceImpl extends BaseServiceImpl 0) { + splitRatio = new BigDecimal(100); + } } - if (!reCalculate) { - return splitRatio; - } - - Integer storeCategoryId = shopStoreBase.getStore_category_id(); - if (ObjectUtil.isEmpty(storeCategoryId)) { - return splitRatio; - } - - // 重新计算分账比例() - ShopBaseStoreCategory shopBaseStoreCategory = shopBaseStoreCategoryService.get(storeCategoryId); - if (ObjectUtil.isEmpty(shopBaseStoreCategory)) { - return splitRatio; - } - - splitRatio = shopBaseStoreCategory.getSplit_ratio(); - - return ObjectUtil.isEmpty(splitRatio) ? new BigDecimal(100) : splitRatio; + return splitRatio; } /**