feat: 重新梳理订单支付流程
parent
6cdd1c1592
commit
5cb0a8e0bf
|
|
@ -9,6 +9,7 @@ import com.ruoyi.xkt.domain.AlipayCallback;
|
||||||
import com.ruoyi.xkt.domain.StoreOrder;
|
import com.ruoyi.xkt.domain.StoreOrder;
|
||||||
import com.ruoyi.xkt.enums.EProcessStatus;
|
import com.ruoyi.xkt.enums.EProcessStatus;
|
||||||
import com.ruoyi.xkt.manager.impl.AliPaymentMangerImpl;
|
import com.ruoyi.xkt.manager.impl.AliPaymentMangerImpl;
|
||||||
|
import com.ruoyi.xkt.service.IAlipayCallbackService;
|
||||||
import com.ruoyi.xkt.service.IStoreOrderService;
|
import com.ruoyi.xkt.service.IStoreOrderService;
|
||||||
import io.swagger.annotations.Api;
|
import io.swagger.annotations.Api;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
|
@ -37,6 +38,8 @@ public class AlipayController extends XktBaseController {
|
||||||
@Autowired
|
@Autowired
|
||||||
private IStoreOrderService storeOrderService;
|
private IStoreOrderService storeOrderService;
|
||||||
@Autowired
|
@Autowired
|
||||||
|
private IAlipayCallbackService alipayCallbackService;
|
||||||
|
@Autowired
|
||||||
private AliPaymentMangerImpl paymentManger;
|
private AliPaymentMangerImpl paymentManger;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -85,7 +88,25 @@ public class AlipayController extends XktBaseController {
|
||||||
return FAILURE;
|
return FAILURE;
|
||||||
}
|
}
|
||||||
//5. 处理支付宝回调信息
|
//5. 处理支付宝回调信息
|
||||||
paymentManger.processAlipayCallback(alipayCallback);
|
AlipayCallback info = alipayCallbackService.getByNotifyId(alipayCallback.getNotifyId());
|
||||||
|
if (info == null) {
|
||||||
|
//保存到数据库
|
||||||
|
info = alipayCallback;
|
||||||
|
alipayCallbackService.insertAlipayCallback(info);
|
||||||
|
}
|
||||||
|
if (!"TRADE_SUCCESS".equals(info.getTradeStatus())) {
|
||||||
|
//非交易支付成功的回调不处理
|
||||||
|
return SUCCESS;
|
||||||
|
}
|
||||||
|
if (info.getRefundFee() != null && !NumberUtil.equals(info.getRefundFee(), BigDecimal.ZERO)) {
|
||||||
|
//如果有退款金额,可能是部分退款的回调,这里不做处理
|
||||||
|
return SUCCESS;
|
||||||
|
}
|
||||||
|
if (EProcessStatus.INIT.getValue().equals(info.getProcessStatus())) {
|
||||||
|
alipayCallbackService.processOrderPay(info);
|
||||||
|
} else {
|
||||||
|
logger.warn("支付回调重复请求处理: {}", info.getId());
|
||||||
|
}
|
||||||
return SUCCESS;
|
return SUCCESS;
|
||||||
} else {
|
} else {
|
||||||
logger.info("支付宝验签未通过:{}", params);
|
logger.info("支付宝验签未通过:{}", params);
|
||||||
|
|
|
||||||
|
|
@ -11,9 +11,10 @@ import com.ruoyi.web.controller.xkt.vo.order.StoreOrderAddReqVO;
|
||||||
import com.ruoyi.web.controller.xkt.vo.order.StoreOrderPayReqVO;
|
import com.ruoyi.web.controller.xkt.vo.order.StoreOrderPayReqVO;
|
||||||
import com.ruoyi.web.controller.xkt.vo.order.StoreOrderPayRespVO;
|
import com.ruoyi.web.controller.xkt.vo.order.StoreOrderPayRespVO;
|
||||||
import com.ruoyi.xkt.dto.order.StoreOrderAddDTO;
|
import com.ruoyi.xkt.dto.order.StoreOrderAddDTO;
|
||||||
|
import com.ruoyi.xkt.dto.order.StoreOrderAddResult;
|
||||||
import com.ruoyi.xkt.dto.order.StoreOrderInfo;
|
import com.ruoyi.xkt.dto.order.StoreOrderInfo;
|
||||||
import com.ruoyi.xkt.enums.EPayChannel;
|
import com.ruoyi.xkt.enums.EPayChannel;
|
||||||
import com.ruoyi.xkt.enums.EPayFrom;
|
import com.ruoyi.xkt.enums.EPayPage;
|
||||||
import com.ruoyi.xkt.manager.PaymentManager;
|
import com.ruoyi.xkt.manager.PaymentManager;
|
||||||
import com.ruoyi.xkt.service.IStoreOrderService;
|
import com.ruoyi.xkt.service.IStoreOrderService;
|
||||||
import io.jsonwebtoken.lang.Assert;
|
import io.jsonwebtoken.lang.Assert;
|
||||||
|
|
@ -26,6 +27,7 @@ import org.springframework.web.bind.annotation.RequestBody;
|
||||||
import org.springframework.web.bind.annotation.RequestMapping;
|
import org.springframework.web.bind.annotation.RequestMapping;
|
||||||
import org.springframework.web.bind.annotation.RestController;
|
import org.springframework.web.bind.annotation.RestController;
|
||||||
|
|
||||||
|
import javax.validation.Valid;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -44,28 +46,30 @@ public class StoreOrderController extends XktBaseController {
|
||||||
|
|
||||||
@PreAuthorize("@ss.hasPermi('system:order:add')")
|
@PreAuthorize("@ss.hasPermi('system:order:add')")
|
||||||
@Log(title = "订单", businessType = BusinessType.INSERT)
|
@Log(title = "订单", businessType = BusinessType.INSERT)
|
||||||
@ApiOperation("创建订单并发起支付")
|
@ApiOperation("创建订单")
|
||||||
@PostMapping("create")
|
@PostMapping("create")
|
||||||
public R<StoreOrderPayRespVO> create(@RequestBody StoreOrderAddReqVO vo) {
|
public R<StoreOrderPayRespVO> create(@Valid @RequestBody StoreOrderAddReqVO vo) {
|
||||||
StoreOrderAddDTO dto = BeanUtil.toBean(vo, StoreOrderAddDTO.class);
|
StoreOrderAddDTO dto = BeanUtil.toBean(vo, StoreOrderAddDTO.class);
|
||||||
dto.setOrderUserId(SecurityUtils.getUserId());
|
dto.setOrderUserId(SecurityUtils.getUserId());
|
||||||
//初始化订单
|
//创建订单并根据参数决定是否发起支付
|
||||||
StoreOrderInfo orderInfo = storeOrderService.createOrder(dto);
|
StoreOrderAddResult result = storeOrderService.createOrder(dto, vo.getBeginPay(),
|
||||||
//发起支付
|
EPayChannel.of(vo.getPayChannel()), EPayPage.of(vo.getPayFrom()));
|
||||||
PaymentManager paymentManager = getPaymentManager(EPayChannel.of(vo.getPayChannel()));
|
|
||||||
String rtnStr = paymentManager.payForOrder(orderInfo.getOrder().getId(), EPayFrom.of(vo.getPayFrom()));
|
|
||||||
//返回信息
|
//返回信息
|
||||||
StoreOrderPayRespVO respVO = new StoreOrderPayRespVO(orderInfo.getOrder().getId(), rtnStr);
|
StoreOrderPayRespVO respVO = new StoreOrderPayRespVO(result.getOrderInfo().getOrder().getId(),
|
||||||
|
result.getPayRtnStr());
|
||||||
return success(respVO);
|
return success(respVO);
|
||||||
}
|
}
|
||||||
|
|
||||||
@PreAuthorize("@ss.hasPermi('system:order:add')")
|
@PreAuthorize("@ss.hasPermi('system:order:add')")
|
||||||
@Log(title = "订单", businessType = BusinessType.OTHER)
|
@Log(title = "订单", businessType = BusinessType.OTHER)
|
||||||
@ApiOperation("重新发起订单支付")
|
@ApiOperation("支付订单")
|
||||||
@PostMapping("pay")
|
@PostMapping("pay")
|
||||||
public R<StoreOrderPayRespVO> pay(@RequestBody StoreOrderPayReqVO vo) {
|
public R<StoreOrderPayRespVO> pay(@Valid @RequestBody StoreOrderPayReqVO vo) {
|
||||||
PaymentManager paymentManager = getPaymentManager(EPayChannel.of(vo.getPayChannel()));
|
PaymentManager paymentManager = getPaymentManager(EPayChannel.of(vo.getPayChannel()));
|
||||||
String rtnStr = paymentManager.payForOrder(vo.getStoreOrderId(), EPayFrom.of(vo.getPayFrom()));
|
//订单支付状态->支付中
|
||||||
|
StoreOrderInfo storeOrderInfo = storeOrderService.preparePayOrder(vo.getStoreOrderId());
|
||||||
|
//调用支付
|
||||||
|
String rtnStr = paymentManager.payOrder(storeOrderInfo, EPayPage.of(vo.getPayFrom()));
|
||||||
StoreOrderPayRespVO respVO = new StoreOrderPayRespVO(vo.getStoreOrderId(), rtnStr);
|
StoreOrderPayRespVO respVO = new StoreOrderPayRespVO(vo.getStoreOrderId(), rtnStr);
|
||||||
return success(respVO);
|
return success(respVO);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -4,6 +4,9 @@ import io.swagger.annotations.ApiModel;
|
||||||
import io.swagger.annotations.ApiModelProperty;
|
import io.swagger.annotations.ApiModelProperty;
|
||||||
import lombok.Data;
|
import lombok.Data;
|
||||||
|
|
||||||
|
import javax.validation.Valid;
|
||||||
|
import javax.validation.constraints.NotEmpty;
|
||||||
|
import javax.validation.constraints.NotNull;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
|
@ -17,6 +20,7 @@ public class StoreOrderAddReqVO {
|
||||||
/**
|
/**
|
||||||
* 档口ID
|
* 档口ID
|
||||||
*/
|
*/
|
||||||
|
@NotNull(message = "档口ID不能为空")
|
||||||
@ApiModelProperty(value = "档口ID")
|
@ApiModelProperty(value = "档口ID")
|
||||||
private Long storeId;
|
private Long storeId;
|
||||||
/**
|
/**
|
||||||
|
|
@ -27,41 +31,49 @@ public class StoreOrderAddReqVO {
|
||||||
/**
|
/**
|
||||||
* 物流ID
|
* 物流ID
|
||||||
*/
|
*/
|
||||||
|
@NotNull(message = "物流ID不能为空")
|
||||||
@ApiModelProperty(value = "物流ID")
|
@ApiModelProperty(value = "物流ID")
|
||||||
private Long expressId;
|
private Long expressId;
|
||||||
/**
|
/**
|
||||||
* 收货人-名称
|
* 收货人-名称
|
||||||
*/
|
*/
|
||||||
|
@NotEmpty(message = "收货人名称不能为空")
|
||||||
@ApiModelProperty(value = "收货人-名称")
|
@ApiModelProperty(value = "收货人-名称")
|
||||||
private String destinationContactName;
|
private String destinationContactName;
|
||||||
/**
|
/**
|
||||||
* 收货人-电话
|
* 收货人-电话
|
||||||
*/
|
*/
|
||||||
|
@NotEmpty(message = "收货人电话不能为空")
|
||||||
@ApiModelProperty(value = "收货人-电话")
|
@ApiModelProperty(value = "收货人-电话")
|
||||||
private String destinationContactPhoneNumber;
|
private String destinationContactPhoneNumber;
|
||||||
/**
|
/**
|
||||||
* 收货人-省编码
|
* 收货人-省编码
|
||||||
*/
|
*/
|
||||||
|
@NotEmpty(message = "收货人省编码不能为空")
|
||||||
@ApiModelProperty(value = "收货人-省编码")
|
@ApiModelProperty(value = "收货人-省编码")
|
||||||
private String destinationProvinceCode;
|
private String destinationProvinceCode;
|
||||||
/**
|
/**
|
||||||
* 收货人-市编码
|
* 收货人-市编码
|
||||||
*/
|
*/
|
||||||
|
@NotEmpty(message = "收货人市编码不能为空")
|
||||||
@ApiModelProperty(value = "收货人-市编码")
|
@ApiModelProperty(value = "收货人-市编码")
|
||||||
private String destinationCityCode;
|
private String destinationCityCode;
|
||||||
/**
|
/**
|
||||||
* 收货人-区县编码
|
* 收货人-区县编码
|
||||||
*/
|
*/
|
||||||
|
@NotEmpty(message = "收货人区县编码不能为空")
|
||||||
@ApiModelProperty(value = "收货人-区县编码")
|
@ApiModelProperty(value = "收货人-区县编码")
|
||||||
private String destinationCountyCode;
|
private String destinationCountyCode;
|
||||||
/**
|
/**
|
||||||
* 收货人-详细地址
|
* 收货人-详细地址
|
||||||
*/
|
*/
|
||||||
|
@NotEmpty(message = "收货人详细地址不能为空")
|
||||||
@ApiModelProperty(value = "收货人-详细地址")
|
@ApiModelProperty(value = "收货人-详细地址")
|
||||||
private String destinationDetailAddress;
|
private String destinationDetailAddress;
|
||||||
/**
|
/**
|
||||||
* 发货方式[1:货其再发 2:有货先发]
|
* 发货方式[1:货其再发 2:有货先发]
|
||||||
*/
|
*/
|
||||||
|
@NotNull(message = "发货方式不能为空")
|
||||||
@ApiModelProperty(value = "发货方式[1:货其再发 2:有货先发]")
|
@ApiModelProperty(value = "发货方式[1:货其再发 2:有货先发]")
|
||||||
private Integer deliveryType;
|
private Integer deliveryType;
|
||||||
/**
|
/**
|
||||||
|
|
@ -72,12 +84,20 @@ public class StoreOrderAddReqVO {
|
||||||
/**
|
/**
|
||||||
* 明细列表
|
* 明细列表
|
||||||
*/
|
*/
|
||||||
|
@Valid
|
||||||
|
@NotEmpty(message = "订单明细不能为空")
|
||||||
@ApiModelProperty(value = "明细列表")
|
@ApiModelProperty(value = "明细列表")
|
||||||
private List<Detail> detailList;
|
private List<Detail> detailList;
|
||||||
|
|
||||||
|
@NotNull(message = "是否发起支付不能为空")
|
||||||
|
@ApiModelProperty(value = "是否发起支付")
|
||||||
|
private Boolean beginPay;
|
||||||
|
|
||||||
|
@NotNull(message = "支付渠道不能为空")
|
||||||
@ApiModelProperty(value = "支付渠道[1:支付宝]")
|
@ApiModelProperty(value = "支付渠道[1:支付宝]")
|
||||||
private Integer payChannel;
|
private Integer payChannel;
|
||||||
|
|
||||||
|
@NotNull(message = "支付来源不能为空")
|
||||||
@ApiModelProperty(value = "支付来源[1:电脑网站 2:手机网站]")
|
@ApiModelProperty(value = "支付来源[1:电脑网站 2:手机网站]")
|
||||||
private Integer payFrom;
|
private Integer payFrom;
|
||||||
|
|
||||||
|
|
@ -85,9 +105,11 @@ public class StoreOrderAddReqVO {
|
||||||
@Data
|
@Data
|
||||||
public static class Detail {
|
public static class Detail {
|
||||||
|
|
||||||
|
@NotNull(message = "商品颜色尺码ID不能为空")
|
||||||
@ApiModelProperty(value = "商品颜色尺码ID")
|
@ApiModelProperty(value = "商品颜色尺码ID")
|
||||||
private Long storeProdColorSizeId;
|
private Long storeProdColorSizeId;
|
||||||
|
|
||||||
|
@NotNull(message = "商品数量不能为空")
|
||||||
@ApiModelProperty(value = "商品数量")
|
@ApiModelProperty(value = "商品数量")
|
||||||
private Integer goodsQuantity;
|
private Integer goodsQuantity;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -4,6 +4,8 @@ import io.swagger.annotations.ApiModel;
|
||||||
import io.swagger.annotations.ApiModelProperty;
|
import io.swagger.annotations.ApiModelProperty;
|
||||||
import lombok.Data;
|
import lombok.Data;
|
||||||
|
|
||||||
|
import javax.validation.constraints.NotNull;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author liangyq
|
* @author liangyq
|
||||||
* @date 2025-04-07 18:16
|
* @date 2025-04-07 18:16
|
||||||
|
|
@ -12,12 +14,15 @@ import lombok.Data;
|
||||||
@Data
|
@Data
|
||||||
public class StoreOrderPayReqVO {
|
public class StoreOrderPayReqVO {
|
||||||
|
|
||||||
|
@NotNull(message = "订单ID不能为空")
|
||||||
@ApiModelProperty(value = "订单ID")
|
@ApiModelProperty(value = "订单ID")
|
||||||
private Long storeOrderId;
|
private Long storeOrderId;
|
||||||
|
|
||||||
|
@NotNull(message = "支付渠道不能为空")
|
||||||
@ApiModelProperty(value = "支付渠道[1:支付宝]")
|
@ApiModelProperty(value = "支付渠道[1:支付宝]")
|
||||||
private Integer payChannel;
|
private Integer payChannel;
|
||||||
|
|
||||||
|
@NotNull(message = "支付来源不能为空")
|
||||||
@ApiModelProperty(value = "支付来源[1:电脑网站 2:手机网站]")
|
@ApiModelProperty(value = "支付来源[1:电脑网站 2:手机网站]")
|
||||||
private Integer payFrom;
|
private Integer payFrom;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,23 +1,27 @@
|
||||||
package com.ruoyi.common.utils;
|
package com.ruoyi.common.utils;
|
||||||
|
|
||||||
import java.util.Collection;
|
|
||||||
import java.util.List;
|
|
||||||
import java.util.stream.Collectors;
|
|
||||||
import org.springframework.security.core.Authentication;
|
|
||||||
import org.springframework.security.core.context.SecurityContextHolder;
|
|
||||||
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
|
|
||||||
import org.springframework.util.PatternMatchUtils;
|
|
||||||
import com.ruoyi.common.constant.Constants;
|
import com.ruoyi.common.constant.Constants;
|
||||||
import com.ruoyi.common.constant.HttpStatus;
|
import com.ruoyi.common.constant.HttpStatus;
|
||||||
import com.ruoyi.common.core.domain.entity.SysRole;
|
import com.ruoyi.common.core.domain.entity.SysRole;
|
||||||
import com.ruoyi.common.core.domain.model.LoginUser;
|
import com.ruoyi.common.core.domain.model.LoginUser;
|
||||||
import com.ruoyi.common.exception.ServiceException;
|
import com.ruoyi.common.exception.ServiceException;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.springframework.security.core.Authentication;
|
||||||
|
import org.springframework.security.core.context.SecurityContextHolder;
|
||||||
|
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
|
||||||
|
import org.springframework.util.PatternMatchUtils;
|
||||||
|
|
||||||
|
import java.util.Collection;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Optional;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 安全服务工具类
|
* 安全服务工具类
|
||||||
*
|
*
|
||||||
* @author ruoyi
|
* @author ruoyi
|
||||||
*/
|
*/
|
||||||
|
@Slf4j
|
||||||
public class SecurityUtils
|
public class SecurityUtils
|
||||||
{
|
{
|
||||||
|
|
||||||
|
|
@ -66,6 +70,25 @@ public class SecurityUtils
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取用户账户
|
||||||
|
*
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public static String getUsernameSafe() {
|
||||||
|
String username = null;
|
||||||
|
try {
|
||||||
|
Authentication auth = getAuthentication();
|
||||||
|
if (auth != null) {
|
||||||
|
LoginUser user = (LoginUser) auth.getPrincipal();
|
||||||
|
username = Optional.ofNullable(user).map(LoginUser::getUsername).orElse(null);
|
||||||
|
}
|
||||||
|
} catch (Exception e) {
|
||||||
|
log.error("获取用户账户异常", e);
|
||||||
|
}
|
||||||
|
return username;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 获取用户
|
* 获取用户
|
||||||
**/
|
**/
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,23 @@
|
||||||
|
package com.ruoyi.xkt.dto.order;
|
||||||
|
|
||||||
|
import lombok.AllArgsConstructor;
|
||||||
|
import lombok.Data;
|
||||||
|
import lombok.NoArgsConstructor;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author liangyq
|
||||||
|
* @date 2025-04-03 13:46
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
@AllArgsConstructor
|
||||||
|
@NoArgsConstructor
|
||||||
|
public class StoreOrderAddResult {
|
||||||
|
/**
|
||||||
|
* 订单信息
|
||||||
|
*/
|
||||||
|
private StoreOrderInfo orderInfo;
|
||||||
|
/**
|
||||||
|
* 三方支付返回信息
|
||||||
|
*/
|
||||||
|
private String payRtnStr;
|
||||||
|
}
|
||||||
|
|
@ -12,6 +12,7 @@ import lombok.Getter;
|
||||||
public enum EOrderAction {
|
public enum EOrderAction {
|
||||||
|
|
||||||
ADD_ORDER(1, "下单"),
|
ADD_ORDER(1, "下单"),
|
||||||
|
PAID_ORDER(2, "支付"),
|
||||||
;
|
;
|
||||||
|
|
||||||
private final Integer value;
|
private final Integer value;
|
||||||
|
|
|
||||||
|
|
@ -9,7 +9,7 @@ import lombok.Getter;
|
||||||
*/
|
*/
|
||||||
@Getter
|
@Getter
|
||||||
@AllArgsConstructor
|
@AllArgsConstructor
|
||||||
public enum EPayFrom {
|
public enum EPayPage {
|
||||||
|
|
||||||
WEB(1, "电脑网站"),
|
WEB(1, "电脑网站"),
|
||||||
WAP(2, "手机网站"),
|
WAP(2, "手机网站"),
|
||||||
|
|
@ -18,8 +18,8 @@ public enum EPayFrom {
|
||||||
private final Integer value;
|
private final Integer value;
|
||||||
private final String label;
|
private final String label;
|
||||||
|
|
||||||
public static EPayFrom of(Integer value) {
|
public static EPayPage of(Integer value) {
|
||||||
for (EPayFrom e : EPayFrom.values()) {
|
for (EPayPage e : EPayPage.values()) {
|
||||||
if (e.getValue().equals(value)) {
|
if (e.getValue().equals(value)) {
|
||||||
return e;
|
return e;
|
||||||
}
|
}
|
||||||
|
|
@ -1,7 +1,8 @@
|
||||||
package com.ruoyi.xkt.manager;
|
package com.ruoyi.xkt.manager;
|
||||||
|
|
||||||
|
import com.ruoyi.xkt.dto.order.StoreOrderInfo;
|
||||||
import com.ruoyi.xkt.enums.EPayChannel;
|
import com.ruoyi.xkt.enums.EPayChannel;
|
||||||
import com.ruoyi.xkt.enums.EPayFrom;
|
import com.ruoyi.xkt.enums.EPayPage;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author liangyq
|
* @author liangyq
|
||||||
|
|
@ -18,10 +19,10 @@ public interface PaymentManager {
|
||||||
/**
|
/**
|
||||||
* 订单支付
|
* 订单支付
|
||||||
*
|
*
|
||||||
* @param storeOrderId
|
* @param order
|
||||||
* @param payFrom
|
* @param payFrom
|
||||||
* @return 跳转页面数据/签名字符串/支付跳转链接/预支付交易会话标识(根据支付渠道&支付来源确定)
|
* @return 跳转页面数据/签名字符串/支付跳转链接/预支付交易会话标识(根据支付渠道&支付来源确定)
|
||||||
*/
|
*/
|
||||||
String payForOrder(Long storeOrderId, EPayFrom payFrom);
|
String payOrder(StoreOrderInfo order, EPayPage payFrom);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,5 @@
|
||||||
package com.ruoyi.xkt.manager.impl;
|
package com.ruoyi.xkt.manager.impl;
|
||||||
|
|
||||||
import cn.hutool.core.util.NumberUtil;
|
|
||||||
import com.alibaba.fastjson2.JSON;
|
import com.alibaba.fastjson2.JSON;
|
||||||
import com.alipay.api.AlipayApiException;
|
import com.alipay.api.AlipayApiException;
|
||||||
import com.alipay.api.AlipayClient;
|
import com.alipay.api.AlipayClient;
|
||||||
|
|
@ -8,23 +7,18 @@ import com.alipay.api.DefaultAlipayClient;
|
||||||
import com.alipay.api.request.AlipayTradePagePayRequest;
|
import com.alipay.api.request.AlipayTradePagePayRequest;
|
||||||
import com.alipay.api.request.AlipayTradeWapPayRequest;
|
import com.alipay.api.request.AlipayTradeWapPayRequest;
|
||||||
import com.ruoyi.common.exception.ServiceException;
|
import com.ruoyi.common.exception.ServiceException;
|
||||||
import com.ruoyi.xkt.domain.AlipayCallback;
|
|
||||||
import com.ruoyi.xkt.dto.order.StoreOrderInfo;
|
|
||||||
import com.ruoyi.xkt.dto.finance.AlipayReqDTO;
|
import com.ruoyi.xkt.dto.finance.AlipayReqDTO;
|
||||||
|
import com.ruoyi.xkt.dto.order.StoreOrderInfo;
|
||||||
import com.ruoyi.xkt.enums.EPayChannel;
|
import com.ruoyi.xkt.enums.EPayChannel;
|
||||||
import com.ruoyi.xkt.enums.EPayFrom;
|
import com.ruoyi.xkt.enums.EPayPage;
|
||||||
|
import com.ruoyi.xkt.enums.EPayStatus;
|
||||||
import com.ruoyi.xkt.manager.PaymentManager;
|
import com.ruoyi.xkt.manager.PaymentManager;
|
||||||
import com.ruoyi.xkt.service.IAlipayCallbackService;
|
|
||||||
import com.ruoyi.xkt.service.IStoreOrderService;
|
|
||||||
import io.jsonwebtoken.lang.Assert;
|
import io.jsonwebtoken.lang.Assert;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
|
||||||
import org.springframework.beans.factory.annotation.Value;
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
|
|
||||||
import java.math.BigDecimal;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author liangyq
|
* @author liangyq
|
||||||
* @date 2025-04-06 19:36
|
* @date 2025-04-06 19:36
|
||||||
|
|
@ -33,6 +27,9 @@ import java.math.BigDecimal;
|
||||||
@Getter
|
@Getter
|
||||||
@Component
|
@Component
|
||||||
public class AliPaymentMangerImpl implements PaymentManager {
|
public class AliPaymentMangerImpl implements PaymentManager {
|
||||||
|
|
||||||
|
private static final String DEFAULT_FORMAT = "json";
|
||||||
|
private static final String PAY_PRODUCT_CODE = "FAST_INSTANT_TRADE_PAY";
|
||||||
/**
|
/**
|
||||||
* 应用ID,您的APPID,收款账号既是您的APPID对应支付宝账号
|
* 应用ID,您的APPID,收款账号既是您的APPID对应支付宝账号
|
||||||
*/
|
*/
|
||||||
|
|
@ -74,29 +71,25 @@ public class AliPaymentMangerImpl implements PaymentManager {
|
||||||
@Value("${alipay.gatewayUrl:https://openapi-sandbox.dl.alipaydev.com/gateway.do}")
|
@Value("${alipay.gatewayUrl:https://openapi-sandbox.dl.alipaydev.com/gateway.do}")
|
||||||
private String gatewayUrl;
|
private String gatewayUrl;
|
||||||
|
|
||||||
@Autowired
|
|
||||||
private IStoreOrderService storeOrderService;
|
|
||||||
@Autowired
|
|
||||||
private IAlipayCallbackService alipayCallbackService;
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public EPayChannel channel() {
|
public EPayChannel channel() {
|
||||||
return EPayChannel.ALI_PAY;
|
return EPayChannel.ALI_PAY;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String payForOrder(Long storeOrderId, EPayFrom payFrom) {
|
public String payOrder(StoreOrderInfo orderInfo, EPayPage payFrom) {
|
||||||
Assert.notNull(storeOrderId);
|
Assert.notNull(orderInfo);
|
||||||
Assert.notNull(payFrom);
|
Assert.notNull(payFrom);
|
||||||
//订单状态更新为支付中
|
if (!EPayStatus.PAYING.getValue().equals(orderInfo.getOrder().getPayStatus())) {
|
||||||
StoreOrderInfo order = storeOrderService.preparePayOrder(storeOrderId);
|
throw new ServiceException("订单[" + orderInfo.getOrder().getOrderNo() + "]支付状态异常");
|
||||||
|
}
|
||||||
AlipayReqDTO reqDTO = new AlipayReqDTO();
|
AlipayReqDTO reqDTO = new AlipayReqDTO();
|
||||||
reqDTO.setOutTradeNo(order.getOrder().getOrderNo());
|
reqDTO.setOutTradeNo(orderInfo.getOrder().getOrderNo());
|
||||||
reqDTO.setTotalAmount(order.getOrder().getTotalAmount().toPlainString());
|
reqDTO.setTotalAmount(orderInfo.getOrder().getTotalAmount().toPlainString());
|
||||||
reqDTO.setSubject("代发订单" + order.getOrder().getOrderNo());
|
reqDTO.setSubject("代发订单" + orderInfo.getOrder().getOrderNo());
|
||||||
reqDTO.setProductCode("FAST_INSTANT_TRADE_PAY"); //这个是固定的
|
reqDTO.setProductCode(PAY_PRODUCT_CODE); //这个是固定的
|
||||||
String reqStr = JSON.toJSONString(reqDTO);
|
String reqStr = JSON.toJSONString(reqDTO);
|
||||||
AlipayClient alipayClient = new DefaultAlipayClient(gatewayUrl, appId, privateKey, "json", charset,
|
AlipayClient alipayClient = new DefaultAlipayClient(gatewayUrl, appId, privateKey, DEFAULT_FORMAT, charset,
|
||||||
alipayPublicKey, signType);
|
alipayPublicKey, signType);
|
||||||
switch (payFrom) {
|
switch (payFrom) {
|
||||||
case WEB:
|
case WEB:
|
||||||
|
|
@ -126,19 +119,4 @@ public class AliPaymentMangerImpl implements PaymentManager {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void processAlipayCallback(AlipayCallback alipayCallback) {
|
|
||||||
AlipayCallback info = alipayCallbackService.getByNotifyId(alipayCallback.getNotifyId());
|
|
||||||
if (info == null) {
|
|
||||||
//保存到数据库
|
|
||||||
info = alipayCallback;
|
|
||||||
alipayCallbackService.insertAlipayCallback(info);
|
|
||||||
}
|
|
||||||
if (info.getRefundFee() != null &&
|
|
||||||
!NumberUtil.equals(info.getRefundFee(), BigDecimal.ZERO)) {
|
|
||||||
//如果有退款金额,可能是部分退款的回调,这里不做处理
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
//TODO
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -24,4 +24,10 @@ public interface IAlipayCallbackService {
|
||||||
*/
|
*/
|
||||||
int insertAlipayCallback(AlipayCallback alipayCallback);
|
int insertAlipayCallback(AlipayCallback alipayCallback);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 处理订单支付结果
|
||||||
|
*
|
||||||
|
* @param info
|
||||||
|
*/
|
||||||
|
void processOrderPay(AlipayCallback info);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -2,7 +2,10 @@ package com.ruoyi.xkt.service;
|
||||||
|
|
||||||
import com.ruoyi.xkt.domain.StoreOrder;
|
import com.ruoyi.xkt.domain.StoreOrder;
|
||||||
import com.ruoyi.xkt.dto.order.StoreOrderAddDTO;
|
import com.ruoyi.xkt.dto.order.StoreOrderAddDTO;
|
||||||
|
import com.ruoyi.xkt.dto.order.StoreOrderAddResult;
|
||||||
import com.ruoyi.xkt.dto.order.StoreOrderInfo;
|
import com.ruoyi.xkt.dto.order.StoreOrderInfo;
|
||||||
|
import com.ruoyi.xkt.enums.EPayChannel;
|
||||||
|
import com.ruoyi.xkt.enums.EPayPage;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author liangyq
|
* @author liangyq
|
||||||
|
|
@ -12,10 +15,14 @@ public interface IStoreOrderService {
|
||||||
/**
|
/**
|
||||||
* 创建订单
|
* 创建订单
|
||||||
*
|
*
|
||||||
* @param storeOrderAddDTO
|
* @param storeOrderAddDTO 订单信息
|
||||||
|
* @param beginPay 是否发起支付
|
||||||
|
* @param payChannel 支付渠道
|
||||||
|
* @param payPage 支付来源
|
||||||
* @return
|
* @return
|
||||||
*/
|
*/
|
||||||
StoreOrderInfo createOrder(StoreOrderAddDTO storeOrderAddDTO);
|
StoreOrderAddResult createOrder(StoreOrderAddDTO storeOrderAddDTO, boolean beginPay, EPayChannel payChannel,
|
||||||
|
EPayPage payPage);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 通过订单号获取订单
|
* 通过订单号获取订单
|
||||||
|
|
@ -31,4 +38,13 @@ public interface IStoreOrderService {
|
||||||
* @param storeOrderId
|
* @param storeOrderId
|
||||||
*/
|
*/
|
||||||
StoreOrderInfo preparePayOrder(Long storeOrderId);
|
StoreOrderInfo preparePayOrder(Long storeOrderId);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 订单支付成果
|
||||||
|
* TODO 更新扣除手续费后的金额
|
||||||
|
*
|
||||||
|
* @param storeOrderId
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
StoreOrderInfo paySuccess(Long storeOrderId);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -2,8 +2,14 @@ package com.ruoyi.xkt.service.impl;
|
||||||
|
|
||||||
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
|
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
|
||||||
import com.ruoyi.xkt.domain.AlipayCallback;
|
import com.ruoyi.xkt.domain.AlipayCallback;
|
||||||
|
import com.ruoyi.xkt.domain.StoreOrder;
|
||||||
|
import com.ruoyi.xkt.dto.order.StoreOrderInfo;
|
||||||
|
import com.ruoyi.xkt.enums.EPayChannel;
|
||||||
|
import com.ruoyi.xkt.enums.EProcessStatus;
|
||||||
import com.ruoyi.xkt.mapper.AlipayCallbackMapper;
|
import com.ruoyi.xkt.mapper.AlipayCallbackMapper;
|
||||||
import com.ruoyi.xkt.service.IAlipayCallbackService;
|
import com.ruoyi.xkt.service.IAlipayCallbackService;
|
||||||
|
import com.ruoyi.xkt.service.IFinanceBillService;
|
||||||
|
import com.ruoyi.xkt.service.IStoreOrderService;
|
||||||
import io.jsonwebtoken.lang.Assert;
|
import io.jsonwebtoken.lang.Assert;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
|
|
@ -18,6 +24,10 @@ public class AlipayCallbackServiceImpl implements IAlipayCallbackService {
|
||||||
|
|
||||||
@Autowired
|
@Autowired
|
||||||
private AlipayCallbackMapper alipayCallbackMapper;
|
private AlipayCallbackMapper alipayCallbackMapper;
|
||||||
|
@Autowired
|
||||||
|
private IStoreOrderService storeOrderService;
|
||||||
|
@Autowired
|
||||||
|
private IFinanceBillService financeBillService;
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
@ -33,4 +43,18 @@ public class AlipayCallbackServiceImpl implements IAlipayCallbackService {
|
||||||
Assert.notNull(alipayCallback);
|
Assert.notNull(alipayCallback);
|
||||||
return alipayCallbackMapper.insert(alipayCallback);
|
return alipayCallbackMapper.insert(alipayCallback);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Transactional
|
||||||
|
@Override
|
||||||
|
public void processOrderPay(AlipayCallback info) {
|
||||||
|
//更新回调状态
|
||||||
|
info.setProcessStatus(EProcessStatus.SUCCESS.getValue());
|
||||||
|
alipayCallbackMapper.updateById(info);
|
||||||
|
//更新订单状态
|
||||||
|
StoreOrder order = storeOrderService.getByOrderNo(info.getOutTradeNo());
|
||||||
|
Assert.notNull(order);
|
||||||
|
StoreOrderInfo orderInfo = storeOrderService.paySuccess(order.getId());
|
||||||
|
//创建收款单
|
||||||
|
financeBillService.createCollectionBillAfterOrderPaid(orderInfo, info.getId(), EPayChannel.ALI_PAY);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -13,9 +13,11 @@ import com.ruoyi.common.utils.bean.BeanValidators;
|
||||||
import com.ruoyi.xkt.domain.*;
|
import com.ruoyi.xkt.domain.*;
|
||||||
import com.ruoyi.xkt.dto.express.ExpressContactDTO;
|
import com.ruoyi.xkt.dto.express.ExpressContactDTO;
|
||||||
import com.ruoyi.xkt.dto.order.StoreOrderAddDTO;
|
import com.ruoyi.xkt.dto.order.StoreOrderAddDTO;
|
||||||
|
import com.ruoyi.xkt.dto.order.StoreOrderAddResult;
|
||||||
import com.ruoyi.xkt.dto.order.StoreOrderInfo;
|
import com.ruoyi.xkt.dto.order.StoreOrderInfo;
|
||||||
import com.ruoyi.xkt.dto.order.StoreOrderOperationRecordAddDTO;
|
import com.ruoyi.xkt.dto.order.StoreOrderOperationRecordAddDTO;
|
||||||
import com.ruoyi.xkt.enums.*;
|
import com.ruoyi.xkt.enums.*;
|
||||||
|
import com.ruoyi.xkt.manager.PaymentManager;
|
||||||
import com.ruoyi.xkt.mapper.*;
|
import com.ruoyi.xkt.mapper.*;
|
||||||
import com.ruoyi.xkt.service.IExpressService;
|
import com.ruoyi.xkt.service.IExpressService;
|
||||||
import com.ruoyi.xkt.service.IOperationRecordService;
|
import com.ruoyi.xkt.service.IOperationRecordService;
|
||||||
|
|
@ -40,21 +42,24 @@ public class StoreOrderServiceImpl implements IStoreOrderService {
|
||||||
@Autowired
|
@Autowired
|
||||||
private StoreOrderDetailMapper storeOrderDetailMapper;
|
private StoreOrderDetailMapper storeOrderDetailMapper;
|
||||||
@Autowired
|
@Autowired
|
||||||
private IExpressService expressService;
|
|
||||||
@Autowired
|
|
||||||
private IOperationRecordService operationRecordService;
|
|
||||||
@Autowired
|
|
||||||
private StoreProductMapper storeProductMapper;
|
private StoreProductMapper storeProductMapper;
|
||||||
@Autowired
|
@Autowired
|
||||||
private StoreProductColorSizeMapper storeProductColorSizeMapper;
|
private StoreProductColorSizeMapper storeProductColorSizeMapper;
|
||||||
@Autowired
|
@Autowired
|
||||||
private StoreProductColorPriceMapper storeProductColorPriceMapper;
|
private StoreProductColorPriceMapper storeProductColorPriceMapper;
|
||||||
@Autowired
|
@Autowired
|
||||||
|
private IExpressService expressService;
|
||||||
|
@Autowired
|
||||||
|
private IOperationRecordService operationRecordService;
|
||||||
|
@Autowired
|
||||||
private IVoucherSequenceService voucherSequenceService;
|
private IVoucherSequenceService voucherSequenceService;
|
||||||
|
@Autowired
|
||||||
|
private List<PaymentManager> paymentManagers;
|
||||||
|
|
||||||
@Transactional
|
@Transactional
|
||||||
@Override
|
@Override
|
||||||
public StoreOrderInfo createOrder(StoreOrderAddDTO storeOrderAddDTO) {
|
public StoreOrderAddResult createOrder(StoreOrderAddDTO storeOrderAddDTO, boolean beginPay, EPayChannel payChannel,
|
||||||
|
EPayPage payPage) {
|
||||||
Long orderUserId = storeOrderAddDTO.getOrderUserId();
|
Long orderUserId = storeOrderAddDTO.getOrderUserId();
|
||||||
Long storeId = storeOrderAddDTO.getStoreId();
|
Long storeId = storeOrderAddDTO.getStoreId();
|
||||||
Long expressId = storeOrderAddDTO.getExpressId();
|
Long expressId = storeOrderAddDTO.getExpressId();
|
||||||
|
|
@ -81,7 +86,7 @@ public class StoreOrderServiceImpl implements IStoreOrderService {
|
||||||
orderDetail.setStoreProdColorSizeId(spcs.getId());
|
orderDetail.setStoreProdColorSizeId(spcs.getId());
|
||||||
orderDetail.setStoreProdId(spcs.getStoreProdId());
|
orderDetail.setStoreProdId(spcs.getStoreProdId());
|
||||||
orderDetail.setDetailStatus(EOrderStatus.PENDING_PAYMENT.getValue());
|
orderDetail.setDetailStatus(EOrderStatus.PENDING_PAYMENT.getValue());
|
||||||
orderDetail.setPayStatus(EPayStatus.INIT.getValue());
|
orderDetail.setPayStatus(beginPay ? EPayStatus.PAYING.getValue() : EPayStatus.INIT.getValue());
|
||||||
orderDetail.setExpressStatus(EExpressStatus.INIT.getValue());
|
orderDetail.setExpressStatus(EExpressStatus.INIT.getValue());
|
||||||
//计算明细费用
|
//计算明细费用
|
||||||
BigDecimal goodsPrice = calcPrice(orderUserId, spcs);
|
BigDecimal goodsPrice = calcPrice(orderUserId, spcs);
|
||||||
|
|
@ -122,7 +127,7 @@ public class StoreOrderServiceImpl implements IStoreOrderService {
|
||||||
order.setOrderNo(orderNo);
|
order.setOrderNo(orderNo);
|
||||||
order.setOrderType(EOrderType.SALES_ORDER.getValue());
|
order.setOrderType(EOrderType.SALES_ORDER.getValue());
|
||||||
order.setOrderStatus(EOrderStatus.PENDING_PAYMENT.getValue());
|
order.setOrderStatus(EOrderStatus.PENDING_PAYMENT.getValue());
|
||||||
order.setPayStatus(EPayStatus.INIT.getValue());
|
order.setPayStatus(beginPay ? EPayStatus.PAYING.getValue() : EPayStatus.INIT.getValue());
|
||||||
order.setOrderRemark(storeOrderAddDTO.getOrderRemark());
|
order.setOrderRemark(storeOrderAddDTO.getOrderRemark());
|
||||||
order.setGoodsQuantity(orderGoodsQuantity);
|
order.setGoodsQuantity(orderGoodsQuantity);
|
||||||
order.setGoodsAmount(orderGoodsAmount);
|
order.setGoodsAmount(orderGoodsAmount);
|
||||||
|
|
@ -160,7 +165,14 @@ public class StoreOrderServiceImpl implements IStoreOrderService {
|
||||||
});
|
});
|
||||||
//操作记录
|
//操作记录
|
||||||
addOperationRecords(orderId, orderDetailIdList, orderUserId, new Date(), EOrderAction.ADD_ORDER);
|
addOperationRecords(orderId, orderDetailIdList, orderUserId, new Date(), EOrderAction.ADD_ORDER);
|
||||||
return new StoreOrderInfo(order, orderDetailList);
|
StoreOrderInfo orderInfo = new StoreOrderInfo(order, orderDetailList);
|
||||||
|
String rtnStr = null;
|
||||||
|
if (beginPay) {
|
||||||
|
//发起支付
|
||||||
|
PaymentManager paymentManager = getPaymentManager(payChannel);
|
||||||
|
rtnStr = paymentManager.payOrder(orderInfo, payPage);
|
||||||
|
}
|
||||||
|
return new StoreOrderAddResult(orderInfo, rtnStr);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
@ -178,33 +190,64 @@ public class StoreOrderServiceImpl implements IStoreOrderService {
|
||||||
Assert.isTrue(EOrderType.SALES_ORDER.getValue().equals(order.getOrderType()),
|
Assert.isTrue(EOrderType.SALES_ORDER.getValue().equals(order.getOrderType()),
|
||||||
"非销售订单无法发起支付");
|
"非销售订单无法发起支付");
|
||||||
Assert.isTrue(BeanValidators.exists(order), "订单不存在");
|
Assert.isTrue(BeanValidators.exists(order), "订单不存在");
|
||||||
|
checkPreparePayStatus(order.getPayStatus());
|
||||||
|
order.setPayStatus(EPayStatus.PAYING.getValue());
|
||||||
|
int orderSuccess = storeOrderMapper.updateById(order);
|
||||||
|
if (orderSuccess == 0) {
|
||||||
|
throw new ServiceException(Constants.VERSION_LOCK_ERROR_COMMON_MSG);
|
||||||
|
}
|
||||||
List<StoreOrderDetail> orderDetails = storeOrderDetailMapper.selectList(
|
List<StoreOrderDetail> orderDetails = storeOrderDetailMapper.selectList(
|
||||||
Wrappers.lambdaQuery(StoreOrderDetail.class)
|
Wrappers.lambdaQuery(StoreOrderDetail.class)
|
||||||
.eq(StoreOrderDetail::getStoreOrderId, storeOrderId)
|
.eq(StoreOrderDetail::getStoreOrderId, storeOrderId)
|
||||||
.eq(SimpleEntity::getDelFlag, Constants.UNDELETED));
|
.eq(SimpleEntity::getDelFlag, Constants.UNDELETED));
|
||||||
checkPreparePayStatus(order.getPayStatus());
|
|
||||||
StoreOrder updateOrder = new StoreOrder();
|
|
||||||
updateOrder.setId(storeOrderId);
|
|
||||||
updateOrder.setPayStatus(EPayStatus.PAYING.getValue());
|
|
||||||
updateOrder.setVersion(order.getVersion());
|
|
||||||
int orderSuccess = storeOrderMapper.updateById(updateOrder);
|
|
||||||
if (orderSuccess == 0) {
|
|
||||||
throw new ServiceException("系统繁忙请稍后再试");
|
|
||||||
}
|
|
||||||
for (StoreOrderDetail orderDetail : orderDetails) {
|
for (StoreOrderDetail orderDetail : orderDetails) {
|
||||||
checkPreparePayStatus(orderDetail.getPayStatus());
|
checkPreparePayStatus(orderDetail.getPayStatus());
|
||||||
StoreOrderDetail orderDetailUpdate = new StoreOrderDetail();
|
orderDetail.setPayStatus(EPayStatus.PAYING.getValue());
|
||||||
orderDetailUpdate.setId(orderDetail.getId());
|
int orderDetailSuccess = storeOrderDetailMapper.updateById(orderDetail);
|
||||||
orderDetailUpdate.setPayStatus(EPayStatus.PAYING.getValue());
|
|
||||||
orderDetailUpdate.setVersion(orderDetail.getVersion());
|
|
||||||
int orderDetailSuccess = storeOrderDetailMapper.updateById(orderDetailUpdate);
|
|
||||||
if (orderDetailSuccess == 0) {
|
if (orderDetailSuccess == 0) {
|
||||||
throw new ServiceException("系统繁忙请稍后再试");
|
throw new ServiceException(Constants.VERSION_LOCK_ERROR_COMMON_MSG);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return new StoreOrderInfo(order, orderDetails);
|
return new StoreOrderInfo(order, orderDetails);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Transactional
|
||||||
|
@Override
|
||||||
|
public StoreOrderInfo paySuccess(Long storeOrderId) {
|
||||||
|
Assert.notNull(storeOrderId);
|
||||||
|
StoreOrder order = storeOrderMapper.selectById(storeOrderId);
|
||||||
|
Assert.isTrue(EOrderType.SALES_ORDER.getValue().equals(order.getOrderType()),
|
||||||
|
"订单类型异常");
|
||||||
|
Assert.isTrue(BeanValidators.exists(order), "订单不存在");
|
||||||
|
Assert.isTrue(order.getPayStatus().equals(EPayStatus.PAYING.getValue()), "订单支付状态异常");
|
||||||
|
order.setPayStatus(EPayStatus.PAID.getValue());
|
||||||
|
//TODO 暂时使用总金额
|
||||||
|
order.setRealTotalAmount(order.getTotalAmount());
|
||||||
|
int orderSuccess = storeOrderMapper.updateById(order);
|
||||||
|
if (orderSuccess == 0) {
|
||||||
|
throw new ServiceException(Constants.VERSION_LOCK_ERROR_COMMON_MSG);
|
||||||
|
}
|
||||||
|
List<StoreOrderDetail> orderDetails = storeOrderDetailMapper.selectList(
|
||||||
|
Wrappers.lambdaQuery(StoreOrderDetail.class)
|
||||||
|
.eq(StoreOrderDetail::getStoreOrderId, storeOrderId)
|
||||||
|
.eq(SimpleEntity::getDelFlag, Constants.UNDELETED));
|
||||||
|
List<Long> orderDetailIdList = new ArrayList<>(orderDetails.size());
|
||||||
|
for (StoreOrderDetail orderDetail : orderDetails) {
|
||||||
|
Assert.isTrue(orderDetail.getPayStatus().equals(EPayStatus.PAYING.getValue()),
|
||||||
|
"订单明细支付状态异常");
|
||||||
|
orderDetail.setPayStatus(EPayStatus.PAID.getValue());
|
||||||
|
orderDetail.setRealTotalAmount(orderDetail.getTotalAmount());
|
||||||
|
int orderDetailSuccess = storeOrderDetailMapper.updateById(orderDetail);
|
||||||
|
if (orderDetailSuccess == 0) {
|
||||||
|
throw new ServiceException(Constants.VERSION_LOCK_ERROR_COMMON_MSG);
|
||||||
|
}
|
||||||
|
orderDetailIdList.add(orderDetail.getId());
|
||||||
|
}
|
||||||
|
//操作记录
|
||||||
|
addOperationRecords(storeOrderId, orderDetailIdList, null, new Date(), EOrderAction.PAID_ORDER);
|
||||||
|
return new StoreOrderInfo(order, orderDetails);
|
||||||
|
}
|
||||||
|
|
||||||
private void checkPreparePayStatus(Integer payStatus) {
|
private void checkPreparePayStatus(Integer payStatus) {
|
||||||
if (!EPayStatus.INIT.getValue().equals(payStatus) && !EPayStatus.PAYING.getValue().equals(payStatus)) {
|
if (!EPayStatus.INIT.getValue().equals(payStatus) && !EPayStatus.PAYING.getValue().equals(payStatus)) {
|
||||||
throw new ServiceException("订单状态异常无法发起支付");
|
throw new ServiceException("订单状态异常无法发起支付");
|
||||||
|
|
@ -328,4 +371,22 @@ public class StoreOrderServiceImpl implements IStoreOrderService {
|
||||||
}
|
}
|
||||||
return spcsMap;
|
return spcsMap;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 根据支付渠道匹配支付类
|
||||||
|
*
|
||||||
|
* @param payChannel
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
private PaymentManager getPaymentManager(EPayChannel payChannel) {
|
||||||
|
if (payChannel == null) {
|
||||||
|
throw new ServiceException("请先选择支付渠道");
|
||||||
|
}
|
||||||
|
for (PaymentManager paymentManager : paymentManagers) {
|
||||||
|
if (paymentManager.channel() == payChannel) {
|
||||||
|
return paymentManager;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
throw new ServiceException("未知支付渠道");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue