src/main/java/com/xcong/excoin/modules/otc/controller/OtcOrderController.java
New file @@ -0,0 +1,60 @@ package com.xcong.excoin.modules.otc.controller; import com.baomidou.mybatisplus.core.metadata.IPage; import com.xcong.excoin.common.response.Result; import com.xcong.excoin.modules.otc.dto.OrderAddDto; import com.xcong.excoin.modules.otc.dto.OrderListDto; import com.xcong.excoin.modules.otc.service.OtcOrderService; import com.xcong.excoin.modules.otc.vo.OrderListVo; import io.swagger.annotations.Api; import io.swagger.annotations.ApiOperation; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; import org.apache.ibatis.annotations.Param; import org.springframework.validation.annotation.Validated; import org.springframework.web.bind.annotation.*; @Slf4j @Validated @RestController @RequestMapping(value = "/api/otcOrder") @RequiredArgsConstructor @Api(value = "OtcOrderController", tags = "otc用户订单接口类") public class OtcOrderController { private final OtcOrderService otcOrderService; @ApiOperation(value = "我要购买") @PostMapping(value = "/buy") public Result buy(@RequestBody OrderAddDto orderAddDto) { otcOrderService.buyOrder(orderAddDto); return Result.ok("购买成功"); } @ApiOperation(value = "我要出售") @PostMapping(value = "/sale") public Result sale(@RequestBody OrderAddDto orderAddDto) { otcOrderService.saleOrder(orderAddDto); return Result.ok("出售成功"); } @ApiOperation(value = "用户订单列表") @PostMapping(value = "/orderList") public Result orderList(@RequestBody OrderListDto orderListDto) { IPage<OrderListVo> page = otcOrderService.findOrderListInPage(orderListDto); return Result.ok(page.getRecords()); } @ApiOperation(value = "已付款,请放币") @PostMapping(value = "/hasPay/{id}") public Result hasPay(@PathVariable("id") Long id) { return null; } @ApiOperation(value = "完成订单") @PostMapping(value = "/finishSalesOrder/{id}") public Result finishOrder(@PathVariable("id") Long id) { return null; } } src/main/java/com/xcong/excoin/modules/otc/dao/OtcEntrustOrderDao.java
@@ -9,6 +9,7 @@ import com.xcong.excoin.modules.otc.vo.EntrustListVo; import org.apache.ibatis.annotations.Param; import java.math.BigDecimal; import java.util.List; public interface OtcEntrustOrderDao extends BaseMapper<OtcEntrustOrder> { @@ -16,4 +17,6 @@ IPage<EntrustListVo> selectEntrustListInPage(@Param("record") EntrustOrderListDto dto, Page<EntrustListVo> page); List<OtcEntrustOrder> selectEntrustOrderByOrderType(@Param("record") OtcEntrustOrder otcEntrustOrder); int updateRemainAmount(@Param("id") Long id, @Param("amount") BigDecimal amount); } src/main/java/com/xcong/excoin/modules/otc/dao/OtcOrderDao.java
@@ -1,7 +1,10 @@ package com.xcong.excoin.modules.otc.dao; import com.baomidou.mybatisplus.core.mapper.BaseMapper; import com.baomidou.mybatisplus.core.metadata.IPage; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.xcong.excoin.modules.otc.entity.OtcOrder; import com.xcong.excoin.modules.otc.vo.OrderListVo; import org.apache.ibatis.annotations.Param; import java.util.List; @@ -9,4 +12,6 @@ public interface OtcOrderDao extends BaseMapper<OtcOrder> { List<OtcOrder> selectOrderListUnFinish(@Param("memberId") Long memberId, @Param("entrustOrderId") Long entrustOrderId); IPage<OrderListVo> selectOrdderListInPage(@Param("record") OtcOrder order, Page<OrderListVo> page); } src/main/java/com/xcong/excoin/modules/otc/dto/OrderAddDto.java
New file @@ -0,0 +1,29 @@ package com.xcong.excoin.modules.otc.dto; import io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; import lombok.Data; import org.jetbrains.annotations.NotNull; import java.math.BigDecimal; @Data @ApiModel(value = "OrderAddDto", description = "提交订单接口参数接收类") public class OrderAddDto { @NotNull @ApiModelProperty(value = "购买USDT数量", example = "120.00") private BigDecimal usdtAmount; @NotNull @ApiModelProperty(value = "CNY金额", example = "120.00") private BigDecimal cnyAmount; @NotNull @ApiModelProperty(value = "委托单ID", example = "1") private Long id; @ApiModelProperty(value = "资金密码 -- 用户出售USDT使用", example = "123456") private String password; } src/main/java/com/xcong/excoin/modules/otc/dto/OrderListDto.java
New file @@ -0,0 +1,21 @@ package com.xcong.excoin.modules.otc.dto; import io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; import lombok.Data; @Data @ApiModel(value = "OtcOrderListDto", description = "订单列表请求参数类") public class OrderListDto { @ApiModelProperty(value = "条数", example = "10") private Integer pageSize; @ApiModelProperty(value = "页码", example = "1") private Integer pageNum; @ApiModelProperty(value = "状态 1-未完成 2-已完成 3-已取消", example = "1") private Integer status; } src/main/java/com/xcong/excoin/modules/otc/entity/OtcOrder.java
@@ -37,6 +37,10 @@ * 订单状态 1-已提交未付款2-已付款3-已完成 */ private Integer status; public static final Integer STATUS_SUBMIT = 1; public static final Integer STATUS_PAY = 2; public static final Integer STATUS_FINISH = 3; public static final Integer STATUS_CANCEL = 4; /** * 付款时间 @@ -59,4 +63,19 @@ * 支付市商ID */ private Long payMbId; /** * 付款人姓名 */ private String payName; /** * 委托单用户ID */ private Long entrustMemberId; /** * 订单类型 B-买 S-卖 */ private String orderType; } src/main/java/com/xcong/excoin/modules/otc/service/OtcOrderService.java
@@ -1,7 +1,17 @@ package com.xcong.excoin.modules.otc.service; import com.baomidou.mybatisplus.core.metadata.IPage; import com.baomidou.mybatisplus.extension.service.IService; import com.xcong.excoin.modules.otc.dto.OrderAddDto; import com.xcong.excoin.modules.otc.dto.OrderListDto; import com.xcong.excoin.modules.otc.entity.OtcOrder; import com.xcong.excoin.modules.otc.vo.OrderListVo; public interface OtcOrderService extends IService<OtcOrder> { void buyOrder(OrderAddDto orderAddDto); void saleOrder(OrderAddDto orderAddDto); IPage<OrderListVo> findOrderListInPage(OrderListDto orderListDto); } src/main/java/com/xcong/excoin/modules/otc/service/impl/OtcOrderServiceImpl.java
@@ -1,13 +1,140 @@ package com.xcong.excoin.modules.otc.service.impl; import cn.hutool.core.bean.BeanUtil; import com.baomidou.mybatisplus.core.metadata.IPage; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; import com.xcong.excoin.common.LoginUserUtils; import com.xcong.excoin.common.exception.GlobalException; import com.xcong.excoin.common.system.service.CommonService; import com.xcong.excoin.modules.member.dao.MemberWalletCoinDao; import com.xcong.excoin.modules.member.entity.MemberEntity; import com.xcong.excoin.modules.member.entity.MemberWalletCoinEntity; import com.xcong.excoin.modules.otc.dao.OtcEntrustOrderDao; import com.xcong.excoin.modules.otc.dto.OrderAddDto; import com.xcong.excoin.modules.otc.dto.OrderListDto; import com.xcong.excoin.modules.otc.entity.OtcEntrustOrder; import com.xcong.excoin.modules.otc.entity.OtcOrder; import com.xcong.excoin.modules.otc.dao.OtcOrderDao; import com.xcong.excoin.modules.otc.service.OtcOrderService; import com.xcong.excoin.modules.otc.vo.OrderListVo; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; import org.springframework.context.annotation.Bean; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import java.math.BigDecimal; import java.util.Date; @Slf4j @Service @RequiredArgsConstructor public class OtcOrderServiceImpl extends ServiceImpl<OtcOrderDao, OtcOrder> implements OtcOrderService { private final OtcEntrustOrderDao otcEntrustOrderDao; private final CommonService commonService; private final MemberWalletCoinDao memberWalletCoinDao; @Override @Transactional(rollbackFor = Exception.class) public void buyOrder(OrderAddDto orderAddDto) { MemberEntity member = LoginUserUtils.getAppLoginUser(); OtcEntrustOrder entrustOrder = otcEntrustOrderDao.selectById(orderAddDto.getId()); if (entrustOrder == null) { throw new GlobalException("委托单不存在"); } if (!OtcEntrustOrder.ORDER_TYPE_S.equals(entrustOrder.getOrderType())) { throw new GlobalException("无法购买"); } if (orderAddDto.getUsdtAmount().compareTo(entrustOrder.getRemainCoinAmount()) > 0) { throw new GlobalException("无足够的USDT"); } BigDecimal cny = orderAddDto.getUsdtAmount().multiply(entrustOrder.getUnitPrice()); log.info("--->{}", cny); if (cny.compareTo(orderAddDto.getCnyAmount()) != 0) { throw new GlobalException("数量与金额不符"); } OtcOrder otcOrder = new OtcOrder(); otcOrder.setOrderNo(commonService.generateOrderNo(member.getId())); otcOrder.setUnitPrice(entrustOrder.getUnitPrice()); otcOrder.setEntrustOrderId(entrustOrder.getId()); otcOrder.setCoinAmount(orderAddDto.getUsdtAmount()); otcOrder.setTotalAmount(orderAddDto.getCnyAmount()); otcOrder.setMemberId(member.getId()); otcOrder.setStatus(OtcOrder.STATUS_SUBMIT); otcOrder.setPayTime(new Date()); otcOrder.setEntrustMemberId(entrustOrder.getMemberId()); otcOrder.setOrderType(OtcEntrustOrder.ORDER_TYPE_B); OtcOrder sale = new OtcOrder(); BeanUtil.copyProperties(otcOrder, sale); sale.setMemberId(entrustOrder.getMemberId()); sale.setOrderType(OtcEntrustOrder.ORDER_TYPE_S); otcEntrustOrderDao.updateRemainAmount(entrustOrder.getId(), orderAddDto.getUsdtAmount().negate()); this.baseMapper.insert(otcOrder); this.baseMapper.insert(sale); } @Override @Transactional(rollbackFor = Exception.class) public void saleOrder(OrderAddDto orderAddDto) { MemberEntity member = LoginUserUtils.getAppLoginUser(); OtcEntrustOrder entrustOrder = otcEntrustOrderDao.selectById(orderAddDto.getId()); if (entrustOrder == null) { throw new GlobalException("委托单不存在"); } if (!OtcEntrustOrder.ORDER_TYPE_B.equals(entrustOrder.getOrderType())) { throw new GlobalException("无法出售"); } BigDecimal cny = orderAddDto.getUsdtAmount().multiply(entrustOrder.getUnitPrice()); if (cny.compareTo(orderAddDto.getCnyAmount()) != 0) { throw new GlobalException("数量与金额不符"); } MemberWalletCoinEntity wallet = memberWalletCoinDao.selectWalletCoinBymIdAndCode(member.getId(), "USDT"); if (wallet.getAvailableBalance().compareTo(orderAddDto.getUsdtAmount()) < 0) { throw new GlobalException("钱包余额不足"); } OtcOrder otcOrder = new OtcOrder(); otcOrder.setOrderNo(commonService.generateOrderNo(member.getId())); otcOrder.setUnitPrice(entrustOrder.getUnitPrice()); otcOrder.setEntrustOrderId(entrustOrder.getId()); otcOrder.setCoinAmount(orderAddDto.getUsdtAmount()); otcOrder.setTotalAmount(orderAddDto.getCnyAmount()); otcOrder.setMemberId(member.getId()); otcOrder.setStatus(OtcOrder.STATUS_SUBMIT); otcOrder.setPayTime(new Date()); otcOrder.setEntrustMemberId(entrustOrder.getMemberId()); otcOrder.setOrderType(OtcEntrustOrder.ORDER_TYPE_S); OtcOrder buy = new OtcOrder(); BeanUtil.copyProperties(otcOrder, buy); buy.setMemberId(entrustOrder.getMemberId()); buy.setOrderType(OtcEntrustOrder.ORDER_TYPE_B); otcEntrustOrderDao.updateRemainAmount(entrustOrder.getId(), orderAddDto.getUsdtAmount().negate()); this.baseMapper.insert(otcOrder); this.baseMapper.insert(buy); memberWalletCoinDao.updateFrozenBalance(member.getId(), wallet.getId(), orderAddDto.getUsdtAmount()); } @Override public IPage<OrderListVo> findOrderListInPage(OrderListDto orderListDto) { MemberEntity member = LoginUserUtils.getAppLoginUser(); Page<OrderListVo> page = new Page<>(orderListDto.getPageNum(), orderListDto.getPageSize()); OtcOrder order = new OtcOrder(); order.setStatus(orderListDto.getStatus()); order.setMemberId(member.getId()); return this.baseMapper.selectOrdderListInPage(order, page); } } src/main/java/com/xcong/excoin/modules/otc/vo/OrderListVo.java
New file @@ -0,0 +1,43 @@ package com.xcong.excoin.modules.otc.vo; import com.fasterxml.jackson.annotation.JsonFormat; import io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; import lombok.Data; import java.math.BigDecimal; import java.util.Date; @Data @ApiModel(value = "OtcOrderListVo", description = "订单列表返回参数类") public class OrderListVo { @ApiModelProperty(value = "订单ID") private Long id; @ApiModelProperty(value = "订单编号") private String orderNo; @ApiModelProperty(value = "单价") private BigDecimal unitPrice; @ApiModelProperty(value = "usdt数量") private BigDecimal amount; @ApiModelProperty(value = "总金额") private BigDecimal totalAmount; @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8") @ApiModelProperty(value = "时间") private Date createTime; @ApiModelProperty(value = "状态 1-已提交 2-已付款 3-已完成 4-已取消") private Integer status; @ApiModelProperty(value = "订单类型 B-买/S-卖") private String orderType; @ApiModelProperty(value = "姓名") private String name; } src/main/resources/mapper/otc/OtcEntrustOrderDao.xml
@@ -42,4 +42,10 @@ </if> </where> </select> <update id="updateRemainAmount"> update otc_entrust_order set remain_coin_amount = remain_coin_amount + ${amount} where id=#{id} </update> </mapper> src/main/resources/mapper/otc/OtcOrderDao.xml
@@ -6,4 +6,35 @@ select * from otc_order where status not in (2,4) and member_id=#{memberId} and entrust_order_id=#{entrustOrderId} </select> <select id="selectOrdderListInPage" resultType="com.xcong.excoin.modules.otc.vo.OrderListVo"> select a.id, a.order_no orderNo, a.unit_price unitPrice, a.coin_amount amount, a.total_amount totalAmount, a.create_time creatTime, a.order_type orderType, b.name name from otc_order a inner join member b on a.member_id=b.id <where> <if test="record!=null"> <if test="record.status != null and record.status == 1"> and a.status in (1, 2) </if> <if test="record.status != null and record.status == 2"> and a.status = 3 </if> <if test="record.status != null and record.status == 3"> and a.status = 4 </if> <if test="record.memberId != null"> and a.member_id = ${record.memberId} </if> </if> </where> </select> </mapper>