Parcourir la source

Merge remote-tracking branch 'origin/master'

lyx il y a 3 mois
Parent
commit
fb1e252a8b
30 fichiers modifiés avec 1052 ajouts et 263 suppressions
  1. 9 0
      alien-entity/src/main/java/shop/alien/entity/second/SecondGoodsRecord.java
  2. 61 0
      alien-entity/src/main/java/shop/alien/entity/second/SecondTradeOperation.java
  3. 4 1
      alien-entity/src/main/java/shop/alien/entity/second/SecondTradeRecord.java
  4. 1 4
      alien-entity/src/main/java/shop/alien/entity/second/vo/SecondGoodsDetailVo.java
  5. 22 0
      alien-entity/src/main/java/shop/alien/entity/second/vo/SecondGoodsRecordDetailVo.java
  6. 4 4
      alien-entity/src/main/java/shop/alien/entity/second/vo/SecondGoodsVo.java
  7. 37 0
      alien-entity/src/main/java/shop/alien/entity/second/vo/SecondTradeRecordVo.java
  8. 3 3
      alien-entity/src/main/java/shop/alien/mapper/StoreCommentMapper.java
  9. 18 1
      alien-entity/src/main/java/shop/alien/mapper/second/SecondGoodsMapper.java
  10. 9 0
      alien-entity/src/main/java/shop/alien/mapper/second/SecondTradeOperationMapper.java
  11. 17 0
      alien-entity/src/main/java/shop/alien/mapper/second/SecondTradeRecordMapper.java
  12. 23 94
      alien-entity/src/main/resources/mapper/ManagementInfoMapper.xml
  13. 3 0
      alien-job/src/main/java/shop/alien/job/jobhandler/VideoModerationJobHandler.java
  14. 1 1
      alien-second/src/main/java/shop/alien/second/controller/AdminSecondGoodsController.java
  15. 2 2
      alien-second/src/main/java/shop/alien/second/controller/SecondGoodsController.java
  16. 41 0
      alien-second/src/main/java/shop/alien/second/platform/PlatformSecondTradeController.java
  17. 18 0
      alien-second/src/main/java/shop/alien/second/service/PlatformSecondTradeService.java
  18. 16 3
      alien-second/src/main/java/shop/alien/second/service/SecondGoodsService.java
  19. 257 0
      alien-second/src/main/java/shop/alien/second/service/impl/PlatformSecondTradeServiceImpl.java
  20. 193 44
      alien-second/src/main/java/shop/alien/second/service/impl/SecondGoodsServiceImpl.java
  21. 56 8
      alien-second/src/main/java/shop/alien/second/service/impl/SecondTradeRecordServiceImpl.java
  22. 55 8
      alien-second/src/main/java/shop/alien/second/task/Task.java
  23. 4 4
      alien-store/src/main/java/shop/alien/store/controller/LifeCouponController.java
  24. 1 1
      alien-store/src/main/java/shop/alien/store/controller/ManagementInfoController.java
  25. 2 2
      alien-store/src/main/java/shop/alien/store/service/LifeCouponService.java
  26. 174 76
      alien-store/src/main/java/shop/alien/store/service/impl/LifeCouponServiceImpl.java
  27. 8 5
      alien-store/src/main/java/shop/alien/store/service/impl/ManagementInfoServiceImpl.java
  28. 2 2
      alien-store/src/main/java/shop/alien/store/service/impl/StoreCommentServiceImpl.java
  29. 6 0
      alien-store/src/main/java/shop/alien/store/service/impl/StoreInfoServiceImpl.java
  30. 5 0
      alien-util/src/main/java/shop/alien/util/common/Constants.java

+ 9 - 0
alien-entity/src/main/java/shop/alien/entity/second/SecondGoodsRecord.java

@@ -20,10 +20,19 @@ public class SecondGoodsRecord implements Serializable {
     @ApiModelProperty(value = "主键ID")
     private Integer id;
 
+
+    @TableField("user_id")
+    @ApiModelProperty(value = "用户ID")
+    private Integer userId;
+
     @TableField("goods_id")
     @ApiModelProperty(value = "商品ID")
     private Integer goodsId;
 
+    @TableField("operation_name")
+    @ApiModelProperty(value = "操作名称")
+    private String operationName;
+
     @TableField("title")
     @ApiModelProperty(value = "商品标题")
     private String title;

+ 61 - 0
alien-entity/src/main/java/shop/alien/entity/second/SecondTradeOperation.java

@@ -0,0 +1,61 @@
+package shop.alien.entity.second;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.baomidou.mybatisplus.extension.activerecord.Model;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.util.Date;
+
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@ApiModel(value="SecondTradeOperation对象", description="二手交易操作表")
+public class SecondTradeOperation extends Model<SecondTradeOperation> {
+    private static final long serialVersionUID = 1L;
+
+    @TableId(value = "id", type = IdType.AUTO)
+    @ApiModelProperty(value = "主键ID")
+    private Integer id;
+
+    @TableField("trade_id")
+    @ApiModelProperty(value = "交易ID")
+    private Integer tradeId;
+
+    @TableField("user_id")
+    @ApiModelProperty(value = "操作人ID")
+    private Integer userId;
+
+    @TableField("type")
+    @ApiModelProperty(value = "操作类型  1-发起交易  2-拒绝交易  3-确认交易  4-签到  5-交易成功  6-交易失败  7-交易取消")
+    private Integer type;
+
+    @TableField("delete_flag")
+    @ApiModelProperty(value = "删除标记 0:未删除 1:已删除")
+    private Integer deleteFlag;
+
+    @TableField("created_time")
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
+    @ApiModelProperty(value = "创建时间")
+    private Date createdTime;
+
+    @TableField("created_user_id")
+    @ApiModelProperty(value = "创建人ID")
+    private Integer createdUserId;
+
+    @TableField("updated_time")
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
+    @ApiModelProperty(value = "修改时间")
+    private Date updatedTime;
+
+    @TableField("updated_user_id")
+    @ApiModelProperty(value = "修改人ID")
+    private Integer updatedUserId;
+}

+ 4 - 1
alien-entity/src/main/java/shop/alien/entity/second/SecondTradeRecord.java

@@ -8,7 +8,6 @@ import lombok.Data;
 import lombok.EqualsAndHashCode;
 import lombok.experimental.Accessors;
 
-import java.io.Serializable;
 import java.math.BigDecimal;
 import java.util.Date;
 
@@ -40,6 +39,10 @@ public class SecondTradeRecord extends Model<SecondTradeRecord> {
     @TableField("goods_id")
     private Integer goodsId;
 
+    @ApiModelProperty(value = "商品记录表id")
+    @TableField("goods_record_id")
+    private Integer goodsRecordId;
+
     @ApiModelProperty(value = "买家id")
     @TableField("buyer_id")
     private Integer buyerId;

+ 1 - 4
alien-entity/src/main/java/shop/alien/entity/second/vo/SecondGoodsDetailVo.java

@@ -20,14 +20,11 @@ public class SecondGoodsDetailVo {
     @ApiModelProperty(value = "商品基本信息")
     private SecondGoodsVo goodsInfo;
 
-    @ApiModelProperty(value = "商品图片列表")
-    private List<StoreImg> imageList;
-
     @ApiModelProperty(value = "商品操作记录集合")
     private List<SecondGoodsRecord> operationRecords;
 
     @ApiModelProperty(value = "商品交易记录集合")
-    private List<SecondTradeRecord> tradeRecords;
+    private List<SecondTradeRecordVo> tradeRecords;
 
     @ApiModelProperty(value = "商品举报集合")
     private List<SecondReportingVo> reports;

+ 22 - 0
alien-entity/src/main/java/shop/alien/entity/second/vo/SecondGoodsRecordDetailVo.java

@@ -1,5 +1,6 @@
 package shop.alien.entity.second.vo;
 
+import com.baomidou.mybatisplus.annotation.TableField;
 import com.fasterxml.jackson.annotation.JsonFormat;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
@@ -9,6 +10,7 @@ import shop.alien.entity.second.SecondGoodsRecord;
 import java.math.BigDecimal;
 import java.util.Date;
 import java.util.List;
+import java.util.Map;
 
 @Data
 @ApiModel("商品操作记录详情VO")
@@ -20,6 +22,22 @@ public class SecondGoodsRecordDetailVo {
     @ApiModelProperty(value = "商品ID")
     private Integer goodsId;
 
+    @TableField(exist = false)
+    @ApiModelProperty(value = "用户电话")
+    private String userPhone;
+
+    @TableField("user_id")
+    @ApiModelProperty(value = "用户ID")
+    private Integer userId;
+
+    @TableField(exist = false)
+    @ApiModelProperty(value = "用户名称")
+    private String userName;
+
+    @TableField("operation_name")
+    @ApiModelProperty(value = "操作名称")
+    private String operationName;
+
     @ApiModelProperty(value = "商品标题")
     private String title;
 
@@ -95,9 +113,13 @@ public class SecondGoodsRecordDetailVo {
     @ApiModelProperty(value = "商品图片列表")
     private List<String> imageUrls;
 
+    @ApiModelProperty(value = "图片集合")
+    private List<Map<String, Object>> imgList;
     public static SecondGoodsRecordDetailVo fromRecord(SecondGoodsRecord record) {
         SecondGoodsRecordDetailVo vo = new SecondGoodsRecordDetailVo();
         vo.setId(record.getId());
+        vo.setUserId(record.getUserId());
+        vo.setOperationName(record.getOperationName());
         vo.setGoodsId(record.getGoodsId());
         vo.setTitle(record.getTitle());
         vo.setDescription(record.getDescription());

+ 4 - 4
alien-entity/src/main/java/shop/alien/entity/second/vo/SecondGoodsVo.java

@@ -11,10 +11,7 @@ import lombok.Data;
 import shop.alien.entity.second.SecondGoods;
 
 import java.text.SimpleDateFormat;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.Date;
-import java.util.List;
+import java.util.*;
 import java.util.concurrent.TimeUnit;
 
 @Data
@@ -32,6 +29,9 @@ public class SecondGoodsVo extends SecondGoods {
     @ApiModelProperty(value = "商品图片")
     private List<String> imgUrl;
 
+    @ApiModelProperty(value = "图片集合")
+    private List<Map<String, Object>> imgList;
+
     @TableField(exist = false)
     @ApiModelProperty(value = "用户名称")
     private String userName;

+ 37 - 0
alien-entity/src/main/java/shop/alien/entity/second/vo/SecondTradeRecordVo.java

@@ -1,5 +1,6 @@
 package shop.alien.entity.second.vo;
 
+import com.alibaba.fastjson2.JSONObject;
 import com.baomidou.mybatisplus.annotation.TableField;
 import com.fasterxml.jackson.annotation.JsonInclude;
 import io.swagger.annotations.ApiModel;
@@ -9,6 +10,7 @@ import lombok.NoArgsConstructor;
 import shop.alien.entity.second.SecondTradeRecord;
 
 import java.math.BigDecimal;
+import java.util.List;
 
 @Data
 @JsonInclude
@@ -16,9 +18,35 @@ import java.math.BigDecimal;
 @ApiModel(value = "SecondTradeRecordVo对象", description = "二手商品交易vo")
 public class SecondTradeRecordVo extends SecondTradeRecord {
 
+    @ApiModelProperty(value = "分页页数")
+    private Integer pageNum;
+
+    @ApiModelProperty(value = "分页条数")
+    private Integer pageSize;
+
+    @ApiModelProperty(value = "买方姓名")
+    private String buyerName;
+
+    @ApiModelProperty(value = "买方联系方式")
+    private String buyerPhone;
+
+    @ApiModelProperty(value = "卖方姓名")
+    private String sellerName;
+
+    @ApiModelProperty(value = "卖方联系方式")
+    private String sellerPhone;
+
     @ApiModelProperty(value = "商品标题")
     private String title;
 
+    @TableField(exist = false)
+    @ApiModelProperty(value = "用户电话")
+    private String userPhone;
+
+    @TableField(exist = false)
+    @ApiModelProperty(value = "用户名称")
+    private String userName;
+
     @ApiModelProperty(value = "商品封面图片")
     private String homeImage;
 
@@ -33,4 +61,13 @@ public class SecondTradeRecordVo extends SecondTradeRecord {
 
     @ApiModelProperty(value = "当前时间是否超过交易时间  0-否  1-是")
     private String timeOutFlag;
+
+    @ApiModelProperty(value = "商品标签")
+    private String goodsLabel;
+
+    @ApiModelProperty(value = "交易流程")
+    private List<JSONObject> operationJsonList;
+
+    @ApiModelProperty(value = "商品信息")
+    private SecondGoodsVo goodsInfo;
 }

+ 3 - 3
alien-entity/src/main/java/shop/alien/mapper/StoreCommentMapper.java

@@ -129,7 +129,7 @@ public interface StoreCommentMapper extends BaseMapper<StoreComment> {
             "WHERE " +
             "business_type = 5 " +
             "AND delete_flag = 0 " +
-            "AND reply_id IS NULL" +
+            "AND reply_id IS NULL " +
             "AND store_id = #{storeId}")
     Map<String, String> getCommentCountAndScoreInfo(@Param("storeId") Integer storeId);
 
@@ -137,7 +137,7 @@ public interface StoreCommentMapper extends BaseMapper<StoreComment> {
     @Select("SELECT " +
             "luo.*,lgbm.group_type groupBuyType,lgbm.group_name groupBuyName,lgbm.image_id groupBuyImgId " +
             "FROM life_user_order luo LEFT JOIN order_coupon_middle ocm ON luo.id = ocm.order_id LEFT JOIN life_group_buy_main lgbm ON ocm.coupon_id = lgbm.id " +
-            "WHERE luo.`status` = 7 " +
+            "WHERE luo.`status` = 7  or luo.`status` = 2 " +
             "AND luo.coupon_type = 2 " +
             "AND luo.delete_flag = 0 " +
             "AND luo.user_id = #{userId} " +
@@ -147,7 +147,7 @@ public interface StoreCommentMapper extends BaseMapper<StoreComment> {
     @Select("SELECT " +
             "luo.*,lgbm.group_type groupBuyType,lgbm.group_name groupBuyName,lgbm.image_id groupBuyImgId " +
             "FROM life_user_order luo LEFT JOIN order_coupon_middle ocm ON luo.id = ocm.order_id LEFT JOIN life_group_buy_main lgbm ON ocm.coupon_id = lgbm.id " +
-            "WHERE luo.`status` = 7 " +
+            "WHERE luo.`status` = 7 or luo.`status` = 2 " +
             "AND luo.coupon_type = 2 " +
             "AND luo.delete_flag = 0 " +
             "AND luo.user_id = #{userId} " +

+ 18 - 1
alien-entity/src/main/java/shop/alien/mapper/second/SecondGoodsMapper.java

@@ -319,7 +319,24 @@ public interface SecondGoodsMapper extends BaseMapper<SecondGoods> {
             "left JOIN second_goods_category sgc2 " +
             "on sg.category_two_id = sgc2.id " +
             "left JOIN life_user lu " +
-            "on lu.id = sg.userId " +
+            "on lu.id = sg.user_id " +
             "${ew.customSqlSegment}")
     SecondGoodsVo getGoodsById(@Param(Constants.WRAPPER) QueryWrapper<SecondGoodsVo> queryWrapper);
+
+    @Select("SELECT " +
+            "sg.*, " +
+            "lu.user_name as userName, " +
+            "lu.user_phone as userPhone, " +
+            "sgc1.category_name as categoryOneName, " +
+            "sgc2.category_name as categoryTwoName " +
+            "FROM second_goods_record sg " +
+            "join second_goods goods on goods.id = sg.goods_id " +
+            "left JOIN second_goods_category sgc1 " +
+            "on sg.category_one_id = sgc1.id " +
+            "left JOIN second_goods_category sgc2 " +
+            "on sg.category_two_id = sgc2.id " +
+            "left JOIN life_user lu " +
+            "on lu.id = goods.user_id " +
+            "${ew.customSqlSegment}")
+    SecondGoodsVo getGoodsRecordById(@Param(Constants.WRAPPER) QueryWrapper<SecondGoodsVo> queryWrapper);
 }

+ 9 - 0
alien-entity/src/main/java/shop/alien/mapper/second/SecondTradeOperationMapper.java

@@ -0,0 +1,9 @@
+package shop.alien.mapper.second;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import org.apache.ibatis.annotations.Mapper;
+import shop.alien.entity.second.SecondTradeOperation;
+
+@Mapper
+public interface SecondTradeOperationMapper extends BaseMapper<SecondTradeOperation> {
+}

+ 17 - 0
alien-entity/src/main/java/shop/alien/mapper/second/SecondTradeRecordMapper.java

@@ -3,7 +3,9 @@ package shop.alien.mapper.second;
 
 import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.baomidou.mybatisplus.core.metadata.IPage;
 import com.baomidou.mybatisplus.core.toolkit.Constants;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import org.apache.ibatis.annotations.Mapper;
 import org.apache.ibatis.annotations.Param;
 import org.apache.ibatis.annotations.Select;
@@ -31,4 +33,19 @@ public interface SecondTradeRecordMapper extends BaseMapper<SecondTradeRecord> {
             "left join second_goods goods on goods.id = trade.goods_id " +
             "${ew.customSqlSegment} ")
     List<SecondTradeRecordVo> getTradeRecord(@Param(Constants.WRAPPER) QueryWrapper<SecondTradeRecord> wrapper);
+
+    @Select("select trade.id, trade.trade_no, trade.goods_id, goods.title, goods.home_image, goods.price, trade.transaction_amount, trade.trade_status, " +
+            "trade.transaction_time, trade.seller_id, trade.transaction_latitude_longitude, trade.transaction_latitude_longitude_address, " +
+            "trade.transaction_location, trade.created_user_id, if (now() >= trade.transaction_time, 1, 0) timeOutFlag " +
+            "from second_trade_record trade " +
+            "left join second_goods goods on goods.id = trade.goods_id " +
+            "${ew.customSqlSegment} ")
+    IPage<SecondTradeRecordVo> getTradeRecordPage(IPage<SecondTradeRecord> page, @Param(Constants.WRAPPER) QueryWrapper<SecondTradeRecord> wrapper);
+
+    @Select("select trade.*, buyer.user_name buyerName, buyer.user_phone buyerPhone, seller.user_name sellerName, seller.user_phone sellerPhone " +
+            "from second_trade_record trade " +
+            "left join life_user buyer on buyer.id = trade.buyer_id " +
+            "left join life_user seller on seller.id = trade.seller_id " +
+            "where trade.id = #{id}")
+    SecondTradeRecordVo getTradeRecordById(@Param("id") Integer id);
 }

+ 23 - 94
alien-entity/src/main/resources/mapper/ManagementInfoMapper.xml

@@ -277,15 +277,9 @@
             ( `status` = 1
             <if test="dataTime != null and dataTime != ''">
                 AND
-                used_time > #{dataTime}
-            </if>
-             )
-           OR ( `status` = 0
-            <if test="dataTime != null and dataTime != ''">
-                AND
                 buy_time > #{dataTime}
             </if>
-               )
+             )
     </select>
     <select id="getTradingVolume" resultType="shop.alien.entity.store.vo.ManagementInfoVo">
         SELECT
@@ -706,7 +700,7 @@
         FROM
             life_user_order
         WHERE
-            `status` = 4
+            `status` = 5
             <if test="dataTime != null and dataTime != ''">
                 AND refund_time > #{dataTime}
             </if>
@@ -717,39 +711,10 @@
         FROM
             life_user_order `order`
         WHERE
-            1 = 1
-            AND (
-            (`order`.`status` = 0
-                <if test="dataTime != null and dataTime != ''">
-                         AND pay_time > #{dataTime}
-                </if>
-            )
-            OR (`order`.`status` = 1
-                <if test="dataTime != null and dataTime != ''">
-                        AND used_time > #{dataTime}
-                </if>
-            )
-            OR (`order`.`status` = 4
-                <if test="dataTime != null and dataTime != ''">
-                        AND refund_time > #{dataTime}
-                </if>
-            )
-            OR (`order`.`status` = 3
+            delete_flag = 0
                 <if test="dataTime != null and dataTime != ''">
-                        AND refund_time > #{dataTime}
+                         AND buy_time > #{dataTime}
                 </if>
-            )
-            OR (`order`.`status` = 99
-                <if test="dataTime != null and dataTime != ''">
-                        AND `order`.created_time > #{dataTime}
-                </if>
-            )
-            OR (`order`.`status` = 98
-                <if test="dataTime != null and dataTime != ''">
-                        AND `order`.created_time > #{dataTime}
-                </if>
-            )
-        )
     </select>
     <select id="getStorePlatformOrderVolume" resultType="shop.alien.entity.store.vo.ManagementInfoVo">
         SELECT
@@ -760,69 +725,33 @@
         ROUND(`order`.final_price, 2) AS final_price,
         CASE
         `order`.`status`
-        WHEN 0 THEN '已付款'
-        WHEN 1 THEN '已完成'
-        WHEN 4 THEN '已退款'
-        WHEN 99 THEN '待付款'
-        WHEN 98 THEN '已取消'
-        WHEN 3 THEN '待退款'
+        WHEN 0 THEN '待支付'
+        WHEN 1 THEN '已支付/待使用'
+        WHEN 2 THEN '已核销'
+        WHEN 3 THEN '已过期'
+        WHEN 4 THEN '已取消'
+        WHEN 5 THEN '已退款'
+        WHEN 6 THEN '退款失败'
+        WHEN 7 THEN '已完成'
         END AS status_name
         FROM
         life_user_order `order`
         LEFT JOIN life_coupon coupon ON `order`.quan_id = coupon.id
         <where>
             1 = 1
-            <choose>
-                <when test="orderType != null and orderType != ''">
-                    AND (`order`.`status` = #{orderType}
-                    <if test="orderType == 99">
-                        or `order`.`status` = "98"
-                    </if>
-                    )
+                <if test="orderType != null and orderType != ''">
                     <choose>
-                        <when test="orderType == 0 and startTime != null and startTime != ''">AND pay_time > #{startTime}</when>
-                        <when test="orderType == 1 and startTime != null and startTime != ''">AND used_time > #{startTime}</when>
-                        <when test="orderType == 4 and startTime != null and startTime != ''">AND refund_time > #{startTime}</when>
-                        <when test="orderType == 3 and startTime != null and startTime != ''">AND refund_time > #{startTime}</when>
-                        <when test="orderType == 98 and startTime != null and startTime != ''">AND `order`.created_time > #{startTime}</when>
-                        <when test="orderType == 99 and startTime != null and startTime != ''">AND `order`.created_time > #{startTime}</when>
+                        <when test="orderType == 2">
+                            AND (`order`.`status` = "0" or `order`.`status` = "4")
+                        </when>
+                        <otherwise>
+                            AND `order`.`status` = #{orderType}
+                        </otherwise>
                     </choose>
-                </when>
-                <otherwise>
-                    AND (
-                    (`order`.`status` = 0
-                        <if test="startTime != null and startTime != ''">
-                            AND pay_time > #{startTime}
-                        </if>
-                    )
-                    OR (`order`.`status` = 1
-                        <if test="startTime != null and startTime != ''">
-                            AND used_time > #{startTime}
-                        </if>
-                    )
-                    OR (`order`.`status` = 4
-                        <if test="startTime != null and startTime != ''">
-                            AND refund_time > #{startTime}
-                        </if>
-                    )
-                    OR (`order`.`status` = 3
-                        <if test="startTime != null and startTime != ''">
-                            AND refund_time > #{startTime}
-                        </if>
-                    )
-                    OR (`order`.`status` = 99
-                        <if test="startTime != null and startTime != ''">
-                            AND `order`.created_time > #{startTime}
-                        </if>
-                    )
-                    OR (`order`.`status` = 98
-                    <if test="startTime != null and startTime != ''">
-                        AND `order`.created_time > #{startTime}
-                    </if>
-                    )
-                )
-                </otherwise>
-            </choose>
+                </if>
+                <if test="startTime != null and startTime != ''">
+                    AND buy_time > #{startTime}
+                </if>
             <if test="orderId != null and orderId != ''">
                 AND `order`.`order_no` like concat('%',#{orderId},'%')
             </if>

+ 3 - 0
alien-job/src/main/java/shop/alien/job/jobhandler/VideoModerationJobHandler.java

@@ -56,7 +56,10 @@ public class VideoModerationJobHandler {
                     if (success) {
                         successCount++;
                         // 处理视频审核结果,更新商品状态
+                        log.info("处理第 {} 个task", successCount);
+                        log.info("TaskId:开始 {} ", task.getTaskId());
                         secondGoodsFeign.processVideoResult(task.getTaskId());
+                        log.info("TaskId:结束 {} ", task.getTaskId());
                     }
                 } catch (Exception e) {
                     log.error("处理视频审核任务时发生异常,任务ID: {}", task.getTaskId(), e);

+ 1 - 1
alien-second/src/main/java/shop/alien/second/controller/AdminSecondGoodsController.java

@@ -49,7 +49,7 @@ public class AdminSecondGoodsController {
     
     @GetMapping("/detail")
     @ApiOperation("管理后台商品详情")
-    public R<SecondGoodsDetailVo> getAdminGoodsDetail(@ApiParam("商品ID") @RequestParam Integer goodsId) {
+    public R<SecondGoodsDetailVo> getAdminGoodsDetail(@ApiParam("商品ID") @RequestParam Integer goodsId) throws Exception {
         log.info("AdminSecondGoodsController.getAdminGoodsDetail?goodsId={}", goodsId);
         
         SecondGoodsDetailVo result = secondGoodsService.getAdminGoodsDetail(goodsId);

+ 2 - 2
alien-second/src/main/java/shop/alien/second/controller/SecondGoodsController.java

@@ -123,7 +123,7 @@ public class SecondGoodsController {
         if (updateResult) {
             // 获取最新的商品信息并记录操作历史
             SecondGoods updatedGoods = secondGoodsService.getById(secondGoods.getId());
-            secondGoodsService.recordGoodsOperation(updatedGoods);
+            secondGoodsService.recordGoodsOperation(updatedGoods,"下架商品");
             return R.success("下架成功");
         } else {
             return R.fail("下架失败");
@@ -144,7 +144,7 @@ public class SecondGoodsController {
             if (removeResult) {
                 // 设置删除标记并记录操作历史
                 goods.setDeleteFlag(1);
-                secondGoodsService.recordGoodsOperation(goods);
+                secondGoodsService.recordGoodsOperation(goods,"删除商品");
                 return R.success("删除成功");
             } else {
                 return R.fail("删除失败");

+ 41 - 0
alien-second/src/main/java/shop/alien/second/platform/PlatformSecondTradeController.java

@@ -0,0 +1,41 @@
+package shop.alien.second.platform;
+
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import io.swagger.annotations.*;
+import lombok.RequiredArgsConstructor;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.web.bind.annotation.*;
+import shop.alien.entity.result.R;
+import shop.alien.entity.second.vo.SecondTradeRecordVo;
+import shop.alien.second.service.PlatformSecondTradeService;
+
+import java.util.List;
+
+@Slf4j
+@Api(tags = {"平台-二手交易记录"})
+@ApiSort(1)
+@CrossOrigin
+@RequiredArgsConstructor
+@RestController
+@RequestMapping("/platformSecondTrade")
+public class PlatformSecondTradeController {
+
+    private final PlatformSecondTradeService secondTradeRecordService;
+
+    @ApiOperation("交易列表")
+    @ApiOperationSupport(order = 1)
+    @PostMapping("/getTradeRecordPage")
+    public R<IPage<SecondTradeRecordVo>> getTradeRecordPage(@RequestBody SecondTradeRecordVo vo) throws Exception {
+        log.info("PlatformSecondTradeController.getTradeRecordPage?vo={}", vo.toString());
+        return R.data(secondTradeRecordService.getTradeRecordPage(vo));
+    }
+
+    @ApiOperation("交易详情")
+    @ApiOperationSupport(order = 2)
+    @GetMapping("/getTradeRecordById")
+    public R<SecondTradeRecordVo> getTradeRecordById(Integer id) throws Exception {
+        log.info("PlatformSecondTradeController.getTradeRecordById?id={}",id);
+        return R.data(secondTradeRecordService.getTradeRecordById(id));
+    }
+
+}

+ 18 - 0
alien-second/src/main/java/shop/alien/second/service/PlatformSecondTradeService.java

@@ -0,0 +1,18 @@
+package shop.alien.second.service;
+
+import com.alibaba.fastjson2.JSONObject;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.service.IService;
+import org.springframework.context.annotation.Lazy;
+import shop.alien.entity.second.SecondTradeRecord;
+import shop.alien.entity.second.vo.SecondTradeRecordVo;
+
+import java.util.List;
+
+public interface PlatformSecondTradeService extends IService<SecondTradeRecord> {
+
+    IPage<SecondTradeRecordVo> getTradeRecordPage(SecondTradeRecordVo vo) throws Exception;
+
+    SecondTradeRecordVo getTradeRecordById(Integer id) throws Exception;
+    List<JSONObject> getOperationJsonList(Integer tradeId) throws Exception;
+}

+ 16 - 3
alien-second/src/main/java/shop/alien/second/service/SecondGoodsService.java

@@ -165,8 +165,7 @@ public interface SecondGoodsService extends IService<SecondGoods> {
      * 记录商品操作历史
      * @param goods 商品信息
      */
-    void recordGoodsOperation(SecondGoods goods);
-
+    void recordGoodsOperation(SecondGoods goods,String operationName);
     /**
      * 管理后台商品列表查询
      * @param page 分页参数
@@ -180,7 +179,7 @@ public interface SecondGoodsService extends IService<SecondGoods> {
      * @param goodsId 商品ID
      * @return 商品详情信息
      */
-    SecondGoodsDetailVo getAdminGoodsDetail(Integer goodsId);
+    SecondGoodsDetailVo getAdminGoodsDetail(Integer goodsId) throws Exception;
 
     /**
      * 获取管理后台商品操作记录详情
@@ -188,4 +187,18 @@ public interface SecondGoodsService extends IService<SecondGoods> {
      * @return 操作记录详情
      */
     SecondGoodsRecordDetailVo getAdminGoodsRecordDetail(Integer recordId);
+
+    /**
+     * 处理商品信息(管理后台使用)
+     * @param goodsId 商品ID
+     * @return 处理后的商品详情信息
+     */
+    SecondGoodsDetailVo dealSecondGoodsInfo(Integer goodsId);
+
+    /**
+     * 处理商品记录信息(管理后台使用)
+     * @param goodsId 商品记录ID
+     * @return 处理后的商品详情信息
+     */
+    SecondGoodsVo dealSecondGoodsRecordInfo(Integer goodsId);
 }

+ 257 - 0
alien-second/src/main/java/shop/alien/second/service/impl/PlatformSecondTradeServiceImpl.java

@@ -0,0 +1,257 @@
+package shop.alien.second.service.impl;
+
+import cn.hutool.core.collection.CollectionUtil;
+import com.alibaba.fastjson2.JSONObject;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import lombok.RequiredArgsConstructor;
+import lombok.extern.slf4j.Slf4j;
+import org.apache.commons.lang3.StringUtils;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.context.annotation.Lazy;
+import org.springframework.stereotype.Service;
+import shop.alien.entity.second.SecondTradeOperation;
+import shop.alien.entity.second.SecondTradeRecord;
+import shop.alien.entity.second.vo.SecondTradeRecordVo;
+import shop.alien.mapper.second.SecondTradeOperationMapper;
+import shop.alien.mapper.second.SecondTradeRecordMapper;
+import shop.alien.second.service.PlatformSecondTradeService;
+import shop.alien.second.service.SecondGoodsService;
+
+import java.time.ZoneId;
+import java.time.format.DateTimeFormatter;
+import java.util.ArrayList;
+import java.util.Comparator;
+import java.util.List;
+import java.util.Objects;
+import java.util.stream.Collectors;
+
+@Slf4j
+@Service
+public class PlatformSecondTradeServiceImpl extends ServiceImpl<SecondTradeRecordMapper, SecondTradeRecord> implements PlatformSecondTradeService {
+
+    @Autowired
+    private SecondTradeRecordMapper secondTradeRecordMapper;
+    @Autowired
+    private SecondTradeOperationMapper secondTradeOperationMapper;
+    @Lazy
+    @Autowired
+    private SecondGoodsService secondGoodsService;
+
+    @Override
+    public IPage<SecondTradeRecordVo> getTradeRecordPage(SecondTradeRecordVo vo) throws Exception {
+        try {
+            Page<SecondTradeRecord> page = new Page<>(vo.getPageNum(), vo.getPageSize());
+            QueryWrapper<SecondTradeRecord> wrapper = new QueryWrapper<>();
+            wrapper.like(null != vo.getGoodsId(), "trade.goods_id", vo.getGoodsId());
+            wrapper.like(StringUtils.isNotBlank(vo.getTradeNo()), "trade.trade_no", vo.getTradeNo());
+            wrapper.eq(null != vo.getTradeStatus(), "trade.trade_status", vo.getTradeStatus());
+            wrapper.eq("trade.delete_flag", 0);
+            wrapper.orderByDesc("trade.created_time");
+            return secondTradeRecordMapper.getTradeRecordPage(page, wrapper);
+        } catch (Exception e) {
+            log.error("PlatformSecondTradeServiceImpl.getTradeRecordPage(): Error Msg={}", e.getMessage());
+            throw new Exception(e);
+        }
+    }
+
+    @Override
+    public SecondTradeRecordVo getTradeRecordById(Integer id) throws Exception {
+        try {
+            // 交易信息
+            SecondTradeRecordVo vo = secondTradeRecordMapper.getTradeRecordById(id);
+            // 交易流程
+            vo.setOperationJsonList(getOperationJsonList(id));
+            // 商品信息
+            vo.setGoodsInfo(secondGoodsService.dealSecondGoodsRecordInfo(vo.getGoodsRecordId()));
+            return vo;
+        } catch (Exception e) {
+            log.error("PlatformSecondTradeServiceImpl.getTradeRecordById(): Error Msg={}", e.getMessage());
+            throw new Exception(e);
+        }
+    }
+    @Override
+    public List<JSONObject> getOperationJsonList(Integer tradeId) throws Exception {
+        try {
+            List<JSONObject> operationJsonList = new ArrayList<>();
+            SecondTradeRecord record = secondTradeRecordMapper.selectById(tradeId);
+            List<SecondTradeOperation> operationList = secondTradeOperationMapper.selectList(
+                    new QueryWrapper<SecondTradeOperation>().eq("trade_id", tradeId).eq("delete_flag", 0));
+
+            // 发起交易
+            JSONObject createJson = new JSONObject();
+            createJson.put("flag", 1);
+            createJson.put("message", "发起交易");
+            createJson.put("time", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm").format(record.getCreatedTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()));
+            operationJsonList.add(createJson);
+
+            // 发起交易后取消交易
+            if (operationList.size() == 2 && 7 == operationList.get(1).getType()) {
+                JSONObject cancelJson = new JSONObject();
+                cancelJson.put("flag", 1);
+                cancelJson.put("message", "取消交易");
+                cancelJson.put("time", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm").format(operationList.get(1).getCreatedTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()));
+                operationJsonList.add(cancelJson);
+                return operationJsonList;
+            }
+
+            // 拒绝
+            SecondTradeOperation refuse = operationList.stream().filter(item -> 2 == item.getType()).findFirst().orElse(null);
+            if (null != refuse) {
+                JSONObject refuseJson = new JSONObject();
+                refuseJson.put("flag", 1);
+                refuseJson.put("message", "拒绝交易");
+                refuseJson.put("time", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm").format(refuse.getCreatedTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()));
+                operationJsonList.add(refuseJson);
+                return operationJsonList;
+            }
+
+            // 确认
+            SecondTradeOperation confirm = operationList.stream().filter(item -> 3 == item.getType()).findFirst().orElse(null);
+            if (null != confirm) {
+                JSONObject confirmJson = new JSONObject();
+                confirmJson.put("flag", 1);
+                confirmJson.put("message", "确认交易");
+                confirmJson.put("time", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm").format(confirm.getCreatedTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()));
+                operationJsonList.add(confirmJson);
+            } else {
+                JSONObject confirmJson = new JSONObject();
+                confirmJson.put("flag", 0);
+                confirmJson.put("message", "等待确认交易");
+                confirmJson.put("time", "");
+                operationJsonList.add(confirmJson);
+            }
+
+            // 确认交易后取消交易
+            if (operationList.size() == 3 && 7 == operationList.get(2).getType()) {
+                JSONObject cancelJson = new JSONObject();
+                cancelJson.put("flag", 1);
+                cancelJson.put("message", "取消交易");
+                cancelJson.put("time", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm").format(operationList.get(2).getCreatedTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()));
+                operationJsonList.add(cancelJson);
+                return operationJsonList;
+            }
+
+            // 签到
+            List<SecondTradeOperation> signIn = operationList.stream().filter(item -> 4 == item.getType()).sorted(Comparator.comparing(SecondTradeOperation::getCreatedTime)).collect(Collectors.toList());
+            // 确认交易
+            List<SecondTradeOperation> successFail = operationList.stream().filter(item -> (5 == item.getType() || 6 == item.getType()) && 0 != item.getUserId()).sorted(Comparator.comparing(SecondTradeOperation::getCreatedTime)).collect(Collectors.toList());
+            // 系统确认的交易失败(超过交易时间12小时未确认成功失败,将自动视为失败)
+            SecondTradeOperation systemFail = operationList.stream().filter(item -> 6 == item.getType() && 0 == item.getUserId()).findFirst().orElse(null);
+
+            if (CollectionUtil.isEmpty(signIn)) {
+                JSONObject signInJson = new JSONObject();
+                signInJson.put("flag", CollectionUtil.isEmpty(successFail) && null == systemFail ? 0 : 2);
+                signInJson.put("message", CollectionUtil.isEmpty(successFail) && null == systemFail ? "等待买方签到" : "买方未签到");
+                signInJson.put("time", "");
+                operationJsonList.add(signInJson);
+
+                signInJson = new JSONObject();
+                signInJson.put("flag", CollectionUtil.isEmpty(successFail) && null == systemFail ? 0 : 2);
+                signInJson.put("message", CollectionUtil.isEmpty(successFail) && null == systemFail ? "等待卖方签到" : "卖方未签到");
+                signInJson.put("time", "");
+                operationJsonList.add(signInJson);
+            } else {
+                // 第一个人签到
+                JSONObject signInJson = new JSONObject();
+                signInJson.put("flag", 1);
+                signInJson.put("message", (Objects.equals(record.getBuyerId(), signIn.get(0).getUserId()) ? "买家" : "卖家" ) + "已签到");
+                signInJson.put("time", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm").format(signIn.get(0).getCreatedTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()));
+                operationJsonList.add(signInJson);
+
+                // 第二个人签到
+                if (signIn.size() > 1) {
+                    JSONObject signInJson2 = new JSONObject();
+                    signInJson2.put("flag", 1);
+                    signInJson2.put("message", (Objects.equals(record.getBuyerId(), signIn.get(1).getUserId()) ? "买家" : "卖家" ) + "已签到");
+                    signInJson2.put("time", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm").format(signIn.get(1).getCreatedTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()));
+                    operationJsonList.add(signInJson2);
+                } else {
+                    JSONObject signInJson2 = new JSONObject();
+                    signInJson2.put("flag", CollectionUtil.isEmpty(successFail) ? 0 : 2);
+                    signInJson2.put("message", (Objects.equals(record.getBuyerId(), signIn.get(0).getUserId()) ? "卖家" : "买家" ) + "未签到");
+                    signInJson2.put("time", "");
+                    operationJsonList.add(signInJson2);
+                }
+            }
+
+            // 签到后取消交易
+            if (CollectionUtil.isEmpty(successFail) && CollectionUtil.isNotEmpty(operationList) && 7 == operationList.get(operationList.size() - 1).getType()) {
+                JSONObject cancelJson = new JSONObject();
+                cancelJson.put("flag", 1);
+                cancelJson.put("message", "取消交易");
+                cancelJson.put("time", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm").format(operationList.get(operationList.size() - 1).getCreatedTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()));
+                operationJsonList.add(cancelJson);
+                return operationJsonList;
+            }
+
+            // 确认交易
+            if (CollectionUtil.isEmpty(successFail)) {
+                JSONObject signInJson = new JSONObject();
+                signInJson.put("flag", null == systemFail ? 0 : 2);
+                signInJson.put("message", null == systemFail ? "等待买方确认交易" : "买方未确认交易");
+                signInJson.put("time", "");
+                operationJsonList.add(signInJson);
+
+                signInJson = new JSONObject();
+                signInJson.put("flag", null == systemFail ? 0 : 2);
+                signInJson.put("message", null == systemFail ? "等待卖方确认交易" : "卖方未确认交易");
+                signInJson.put("time", "");
+                operationJsonList.add(signInJson);
+            } else {
+                // 第一个人确认交易
+                JSONObject successFailJson = new JSONObject();
+                successFailJson.put("flag", 1);
+                successFailJson.put("message", (Objects.equals(record.getBuyerId(), successFail.get(0).getUserId()) ? "买家" : "卖家" ) + "确认交易" +
+                        (5 == successFail.get(0).getType() ? "成功" : "失败"));
+                successFailJson.put("time", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm").format(successFail.get(0).getCreatedTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()));
+                operationJsonList.add(successFailJson);
+
+                // 第二个人确认交易
+                if (successFail.size() > 1) {
+                    JSONObject successFailJson2 = new JSONObject();
+                    successFailJson2.put("flag", 1);
+                    successFailJson2.put("message", (Objects.equals(record.getBuyerId(), successFail.get(1).getUserId()) ? "买家" : "卖家" ) + "确认交易" +
+                            (5 == successFail.get(1).getType() ? "成功" : "失败"));
+                    successFailJson2.put("time", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm").format(successFail.get(1).getCreatedTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()));
+                    operationJsonList.add(successFailJson2);
+                } else {
+                    JSONObject successFailJson2 = new JSONObject();
+                    successFailJson2.put("flag", Objects.equals(record.getSellerId(), successFail.get(0).getUserId()) ? 2 : 0);
+                    successFailJson2.put("message", (Objects.equals(record.getBuyerId(), successFail.get(0).getUserId()) ? "卖家" : "买家" ) + "未确认交易");
+                    successFailJson2.put("time", "");
+                    operationJsonList.add(successFailJson2);
+                }
+            }
+
+            // 交易完成
+            if (4 == record.getTradeStatus()) {
+                JSONObject finishJson = new JSONObject();
+                finishJson.put("flag", 1);
+                finishJson.put("message", "交易成功");
+                finishJson.put("time", "");
+                operationJsonList.add(finishJson);
+            } else if (5 == record.getTradeStatus()) {
+                JSONObject finishJson = new JSONObject();
+                finishJson.put("flag", 1);
+                finishJson.put("message", "交易失败");
+                finishJson.put("time", "");
+                operationJsonList.add(finishJson);
+            } else {
+                JSONObject finishJson = new JSONObject();
+                finishJson.put("flag", 0);
+                finishJson.put("message", "交易成功");
+                finishJson.put("time", "");
+                operationJsonList.add(finishJson);
+            }
+
+            return operationJsonList;
+        } catch (Exception e) {
+            log.error("PlatformSecondTradeServiceImpl.getOperationJsonList Error Msg={}", e.getMessage());
+            throw new Exception(e);
+        }
+    }
+
+}

+ 193 - 44
alien-second/src/main/java/shop/alien/second/service/impl/SecondGoodsServiceImpl.java

@@ -4,7 +4,6 @@ import cn.hutool.core.collection.CollectionUtil;
 import com.alibaba.fastjson2.JSON;
 import com.alibaba.fastjson2.JSONArray;
 import com.alibaba.fastjson2.JSONObject;
-import com.alibaba.nacos.api.config.annotation.NacosValue;
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
@@ -17,7 +16,7 @@ import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.BeanUtils;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.beans.factory.annotation.Value;
-import org.springframework.cloud.context.config.annotation.RefreshScope;
+import org.springframework.context.annotation.Lazy;
 import org.springframework.stereotype.Service;
 import org.springframework.util.StringUtils;
 import shop.alien.entity.SecondVideoTask;
@@ -34,6 +33,7 @@ import shop.alien.mapper.second.SecondGoodsMapper;
 import shop.alien.mapper.second.SecondGoodsRecordMapper;
 import shop.alien.mapper.second.SecondTradeRecordMapper;
 import shop.alien.second.feign.AlienStoreFeign;
+import shop.alien.second.service.PlatformSecondTradeService;
 import shop.alien.second.service.SecondGoodsService;
 import shop.alien.second.service.VideoModerationService;
 import shop.alien.util.common.Constants;
@@ -42,7 +42,6 @@ import shop.alien.util.common.VideoUtils;
 import shop.alien.util.common.safe.*;
 
 import java.math.BigDecimal;
-import java.text.SimpleDateFormat;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Collections;
@@ -146,6 +145,11 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
      */
     private final StoreDictionaryMapper storeDictionaryMapper;
 
+    /**
+     * 交易记录服务
+     */
+    private final PlatformSecondTradeService platformSecondTradeService;
+
     @Override
     public SecondGoodsRecordDetailVo getAdminGoodsRecordDetail(Integer recordId) {
         // 1. 获取商品操作记录基本信息
@@ -157,11 +161,24 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
         // 2. 转换为VO对象
         SecondGoodsRecordDetailVo detailVo = SecondGoodsRecordDetailVo.fromRecord(record);
 
+        if (record.getUserId() != null){
+            // 获取联系人
+            QueryWrapper<LifeUser> userQueryWrapper = new QueryWrapper<>();
+            userQueryWrapper.lambda()
+                    .eq(LifeUser::getId, record.getUserId())
+                    .eq(LifeUser::getDeleteFlag, Constants.DeleteFlag.NOT_DELETED);
+            LifeUser user = lifeUserMapper.selectOne(userQueryWrapper);
+
+            detailVo.setUserName(user.getUserName());
+            detailVo.setUserPhone(user.getUserPhone());
+        }
+
+
         // 3. 获取商品图片列表
         QueryWrapper<StoreImg> imageQueryWrapper = new QueryWrapper<>();
         imageQueryWrapper.lambda()
-                .eq(StoreImg::getStoreId, record.getGoodsId())
-                .eq(StoreImg::getImgType, Constants.ImageType.SECOND_HAND_GOODS)
+                .eq(StoreImg::getStoreId, record.getId())
+                .eq(StoreImg::getImgType, Constants.ImageType.SECOND_HAND_RECORD)
                 .eq(StoreImg::getDeleteFlag, Constants.DeleteFlag.NOT_DELETED)
                 .orderByAsc(StoreImg::getImgSort);
         List<StoreImg> imageList = storeImgMapper.selectList(imageQueryWrapper);
@@ -171,6 +188,8 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
             List<String> imageUrls = imageList.stream()
                     .map(StoreImg::getImgUrl)
                     .collect(Collectors.toList());
+            List<Map<String, Object>> imgList = processReportImages(imageUrls,2);
+            detailVo.setImgList(imgList);
             detailVo.setImageUrls(imageUrls);
         }
 
@@ -178,25 +197,9 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
     }
 
     @Override
-    public SecondGoodsDetailVo getAdminGoodsDetail(Integer goodsId) {
-        SecondGoodsDetailVo detailVo = new SecondGoodsDetailVo();
-        QueryWrapper<SecondGoodsVo> goodsVoQueryWrapper = new QueryWrapper<>();
-        goodsVoQueryWrapper.lambda()
-                .eq(SecondGoodsVo::getId, goodsId);
-        // 1. 获取商品基本信息
-        SecondGoodsVo goodsInfo = secondGoodsMapper.getGoodsById(goodsVoQueryWrapper);
-        detailVo.setGoodsInfo(goodsInfo);
-        
-        // 2. 获取商品图片列表
-        QueryWrapper<StoreImg> imageQueryWrapper = new QueryWrapper<>();
-        imageQueryWrapper.lambda()
-                .eq(StoreImg::getStoreId, goodsId)
-                .eq(StoreImg::getImgType, Constants.ImageType.SECOND_HAND_GOODS)
-                .eq(StoreImg::getDeleteFlag, Constants.DeleteFlag.NOT_DELETED)
-                .orderByAsc(StoreImg::getImgSort);
-        List<StoreImg> imageList = storeImgMapper.selectList(imageQueryWrapper);
-        detailVo.setImageList(imageList);
-        
+    public SecondGoodsDetailVo getAdminGoodsDetail(Integer goodsId) throws Exception {
+        // 基本信息
+        SecondGoodsDetailVo detailVo =  dealSecondGoodsInfo(goodsId);
         // 3. 获取商品操作记录集合
         QueryWrapper<SecondGoodsRecord> recordQueryWrapper = new QueryWrapper<>();
         recordQueryWrapper.lambda()
@@ -210,10 +213,26 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
         tradeQueryWrapper.eq("goods_id", goodsId)
                 .orderByDesc("transaction_time");
         List<SecondTradeRecord> tradeRecords = secondTradeRecordMapper.selectList(tradeQueryWrapper);
-
-        // TODO 处理交易步骤
-
-        detailVo.setTradeRecords(tradeRecords);
+        // 处理交易步骤 调取 PlatformSecondTradeServiceImpl.getOperationJsonList
+        List<SecondTradeRecordVo> secondTradeRecordVos = Lists.newArrayList();
+        if (CollectionUtil.isNotEmpty(tradeRecords)){
+            for (SecondTradeRecord tradeRecord : tradeRecords) {
+                SecondTradeRecordVo secondTradeRecordVo = new SecondTradeRecordVo();
+                BeanUtils.copyProperties(tradeRecord, secondTradeRecordVo);
+                // 交易节点
+                secondTradeRecordVo.setOperationJsonList(platformSecondTradeService.getOperationJsonList(tradeRecord.getId()));
+                // 获取联系人
+                QueryWrapper<LifeUser> userQueryWrapper = new QueryWrapper<>();
+                userQueryWrapper.lambda()
+                        .eq(LifeUser::getId, secondTradeRecordVo.getBuyerId())
+                        .eq(LifeUser::getDeleteFlag, Constants.DeleteFlag.NOT_DELETED);
+                LifeUser user = lifeUserMapper.selectOne(userQueryWrapper);
+                secondTradeRecordVo.setUserName(user.getUserName());
+                secondTradeRecordVo.setUserPhone(user.getUserPhone());
+                secondTradeRecordVos.add(secondTradeRecordVo);
+            }
+        }
+        detailVo.setTradeRecords(secondTradeRecordVos);
         
         // 5. 获取商品举报集合
         QueryWrapper<LifeUserViolation> reportQueryWrapper = new QueryWrapper<>();
@@ -229,16 +248,76 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
         
         return detailVo;
     }
-    
+
+    @Override
+    public SecondGoodsDetailVo dealSecondGoodsInfo(Integer goodsId) {
+        SecondGoodsDetailVo SecondGoodsDetailVo = new SecondGoodsDetailVo();
+        QueryWrapper<SecondGoodsVo> goodsVoQueryWrapper = new QueryWrapper<>();
+        goodsVoQueryWrapper
+                .eq("sg.id", goodsId);
+        // 1. 获取商品基本信息
+        SecondGoodsVo goodsInfo = secondGoodsMapper.getGoodsById(goodsVoQueryWrapper);
+
+        // 2. 获取商品图片列表
+        QueryWrapper<StoreImg> imageQueryWrapper = new QueryWrapper<>();
+        imageQueryWrapper.lambda()
+                .eq(StoreImg::getStoreId, goodsId)
+                .eq(StoreImg::getImgType, Constants.ImageType.SECOND_HAND_GOODS)
+                .eq(StoreImg::getDeleteFlag, Constants.DeleteFlag.NOT_DELETED)
+                .orderByAsc(StoreImg::getImgSort);
+        List<StoreImg> imageList = storeImgMapper.selectList(imageQueryWrapper);
+        // 提取图片URL列表
+        if (CollectionUtil.isNotEmpty(imageList)) {
+            List<String> imageUrls = imageList.stream()
+                    .map(StoreImg::getImgUrl)
+                    .collect(Collectors.toList());
+            List<Map<String, Object>> imgList = processReportImages(imageUrls,2);
+            goodsInfo.setImgList(imgList);
+            goodsInfo.setImgUrl(imageUrls);
+        }
+        SecondGoodsDetailVo.setGoodsInfo(goodsInfo);
+        return SecondGoodsDetailVo;
+    }
+
+    @Override
+    public SecondGoodsVo dealSecondGoodsRecordInfo(Integer goodsId) {
+        QueryWrapper<SecondGoodsVo> goodsVoQueryWrapper = new QueryWrapper<>();
+        goodsVoQueryWrapper.eq("sg.id", goodsId);
+        // 1. 获取商品基本信息
+        SecondGoodsVo goodsInfo = secondGoodsMapper.getGoodsRecordById(goodsVoQueryWrapper);
+
+        // 2. 获取商品图片列表
+        QueryWrapper<StoreImg> imageQueryWrapper = new QueryWrapper<>();
+        imageQueryWrapper.lambda()
+                .eq(StoreImg::getStoreId, goodsId)
+                .eq(StoreImg::getImgType, Constants.ImageType.SECOND_HAND_RECORD)
+                .eq(StoreImg::getDeleteFlag, Constants.DeleteFlag.NOT_DELETED)
+                .orderByAsc(StoreImg::getImgSort);
+        List<StoreImg> imageList = storeImgMapper.selectList(imageQueryWrapper);
+        // 提取图片URL列表
+        if (CollectionUtil.isNotEmpty(imageList)) {
+            List<String> imageUrls = imageList.stream()
+                    .map(StoreImg::getImgUrl)
+                    .collect(Collectors.toList());
+            List<Map<String, Object>> imgList = processReportImages(imageUrls,2);
+            goodsInfo.setImgList(imgList);
+            goodsInfo.setImgUrl(imageUrls);
+        }
+        return goodsInfo;
+    }
+
     /**
      * 记录商品操作历史
      * @param goods 商品信息
      */
     @Override
-    public void recordGoodsOperation(SecondGoods goods) {
+    public void recordGoodsOperation(SecondGoods goods,String operationName) {
         try {
+            log.warn("开始创建操作历史: {},{} ", goods,operationName);
             SecondGoodsRecord record = new SecondGoodsRecord();
+            record.setOperationName(operationName);
             record.setGoodsId(goods.getId());
+            record.setUserId(goods.getUserId());
             record.setTitle(goods.getTitle());
             record.setDescription(goods.getDescription());
             // 价格转换
@@ -273,11 +352,47 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
             record.setAddressText(goods.getAddressText());
             
             secondGoodsRecordMapper.insert(record);
+            log.warn("创建操作历史结束: {} ", record);
+            // 保存图片信息
+            saveRecordGoodsImages(record);
         } catch (Exception e) {
             log.error("记录商品操作历史时发生异常", e);
         }
     }
-    
+
+
+    /**
+     * 保存二手商品记录图片类型信息
+     *
+     * @param record 保存后的商品记录
+     */
+    private void saveRecordGoodsImages(SecondGoodsRecord record ) {
+
+        log.info("创建操作历图片史开始: {} ", record);
+        // 获取商品图片列表
+        QueryWrapper<StoreImg> query = new QueryWrapper<>();
+        query.lambda().eq(StoreImg::getStoreId, record.getGoodsId())
+                .eq(StoreImg::getImgType, Constants.ImageType.SECOND_HAND_GOODS);
+        List<StoreImg> storeImgs = storeImgMapper.selectList(query);
+        // 保存前先把原有的删除
+        storeImgs.forEach(storeImgModel -> {
+            StoreImg storeImg = new StoreImg();
+            storeImg.setStoreId(record.getId());
+            storeImg.setImgType(Constants.ImageType.SECOND_HAND_RECORD);
+            storeImg.setImgSort(storeImgModel.getImgSort());
+            storeImg.setImgDescription("二手商品记录图片类型");
+            storeImg.setDeleteFlag(Constants.DeleteFlag.NOT_DELETED);
+            storeImg.setCreatedTime(new Date());
+            storeImg.setUpdatedTime(new Date());
+            storeImg.setCreatedUserId(1);
+            storeImg.setUpdatedUserId(1);
+            storeImg.setImgUrl(storeImgModel.getImgUrl());
+            // 保存图片 插入store_img数据库
+            storeImgMapper.insert(storeImg);
+            log.info("创建操作历图片结束: {} ", storeImg);
+        });
+    }
+
     /**
      * 批量转换举报信息为SecondReportingVo对象
      * @param reports 举报信息列表
@@ -315,7 +430,7 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
             SecondReportingVo reportingVo = new SecondReportingVo();
 
             // 查询用户表 根据举报用户类型和举报用户ID 查询 life_user 表 user_phone
-            LifeUser reporter = lifeUserMapper.selectById(report.getReportedUserId());
+            LifeUser reporter = lifeUserMapper.selectById(report.getReportingUserId());
             if (reporter != null) {
                 // 处理举报用户名称  life_user 表 user_name
                 reportingVo.setReportingUserName(reporter.getUserName());
@@ -347,7 +462,8 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
             }
             // 处理举报凭证图片
             if (StringUtils.hasText(report.getReportEvidenceImg())) {
-                List<Map<String, Object>> imgList = processReportImages(report.getReportEvidenceImg());
+                List<String> urlList = Arrays.asList(report.getReportEvidenceImg().split(","));
+                List<Map<String, Object>> imgList = processReportImages(urlList,1);
                 reportingVo.setImgList(imgList);
             }
             
@@ -359,12 +475,12 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
 
     /**
      * 处理举报凭证图片
-     * @param reportEvidenceImg 图片URL字符串
+     * @param urlList 图片URL集合
+     * @param type  类型 1-举报 2-商品
      * @return 图片列表
      */
-    private List<Map<String, Object>> processReportImages(String reportEvidenceImg) {
+    private List<Map<String, Object>> processReportImages(List<String> urlList, Integer type) {
         List<Map<String, Object>> list = new ArrayList<>();
-        List<String> urlList = Arrays.asList(reportEvidenceImg.split(","));
         List<String> videoList = new ArrayList<>();
         List<String> videoFileType = Arrays.asList("mp4", "avi", "flv", "mkv", "rmvb", "wmv", "3gp", "mov");
 
@@ -380,11 +496,13 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
                 contains = urlList.get(i).substring(0, lastDotIndex);
             }
 
-            if (!videoList.contains(contains)) {
+            if (!StringUtils.isEmpty(contains)) {
                 videoList.add(contains);
                 if (videoFileType.contains(fileType.toLowerCase())) {
                     map.put("type", "video");
-                    map.put("imgUrl", urlList.get(i + 1));
+                    if (type == 1){
+                        map.put("imgUrl", urlList.get(i + 1));
+                    }
                     map.put("videoUrl", urlList.get(i));
                 } else {
                     map.put("type", "image");
@@ -530,7 +648,16 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
         // 发送审核成功消息
         sendMessage(goods);
         // 上架 记录商品操作历史
-        recordGoodsOperation(goods);
+        String operationName = "";
+        QueryWrapper<SecondGoodsRecord> queryWrapper = new QueryWrapper<>();
+        queryWrapper.eq("goods_id", goods.getId());
+        List<SecondGoodsRecord> recordList = secondGoodsRecordMapper.selectList(queryWrapper);
+        if (CollectionUtil.isNotEmpty(recordList)){
+            operationName = "重新发布";
+        }else {
+            operationName = "首次发布";
+        }
+        recordGoodsOperation(goods, operationName);
     }
 
     /**
@@ -714,7 +841,7 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
                     updateById(goods);
                     createGoodsAudit(goods, "", SecondGoodsStatusEnum.UNDER_REVIEW.getCode());
                     // 审核中,记录操作历史
-                    recordGoodsOperation(goods);
+//                    recordGoodsOperation(goods);
                     return true; // 异步处理,直接返回
                 }
             }
@@ -730,7 +857,16 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
         // 发送审核成功消息
         sendMessage(goods);
         // 审核成功,记录操作历史
-        recordGoodsOperation(goods);
+        String operationName = "";
+        QueryWrapper<SecondGoodsRecord> queryWrapper = new QueryWrapper<>();
+        queryWrapper.eq("goods_id", goods.getId());
+        List<SecondGoodsRecord> recordList = secondGoodsRecordMapper.selectList(queryWrapper);
+        if (CollectionUtil.isNotEmpty(recordList)){
+            operationName = "重新发布";
+        }else {
+            operationName = "首次发布";
+        }
+        recordGoodsOperation(goods, operationName);
         return true;
     }
     
@@ -797,7 +933,7 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
             updateById(secondGoods);
         }
         // 保存前先把原有的删除
-        storeImgMapper.delete(new LambdaUpdateWrapper<StoreImg>().eq(StoreImg::getStoreId, savedGoodsId));
+        storeImgMapper.delete(new LambdaUpdateWrapper<StoreImg>().eq(StoreImg::getStoreId, savedGoodsId).eq(StoreImg::getImgType, Constants.ImageType.SECOND_HAND_GOODS));
         // 批量保存图片信息
         for(int i = 0; i < goods.getImgUrl().size(); i++){
             StoreImg storeImg = new StoreImg();
@@ -1353,7 +1489,19 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
                 // 发送审核成功消息
                 sendMessage(goods);
                 // 审核成功,记录操作历史
-                recordGoodsOperation(goods);
+                // 审核成功,记录操作历史
+                String operationName = "";
+                QueryWrapper<SecondGoodsRecord> queryRecordWrapper = new QueryWrapper<>();
+                queryRecordWrapper.eq("goods_id", goods.getId());
+                log.info("查询操作记录开始 goods_id: {}", goods.getId());
+                List<SecondGoodsRecord> recordList = secondGoodsRecordMapper.selectList(queryRecordWrapper);
+                log.info("查询操作记录结束 recordList: {}", recordList);
+                if (CollectionUtil.isNotEmpty(recordList)){
+                    operationName = "重新发布";
+                }else {
+                    operationName = "首次发布";
+                }
+                recordGoodsOperation(goods, operationName);
             } else {
                 // 审核不通过
                 goods.setGoodsStatus(SecondGoodsStatusEnum.REVIEW_FAILED.getCode());
@@ -1594,7 +1742,8 @@ public class SecondGoodsServiceImpl extends ServiceImpl<SecondGoodsMapper, Secon
                 queryWrapper.eq("sg.delete_flag", Constants.DeleteFlag.DELETED);
             } else {
                 // 其他状态按照商品状态进行查询,并且删除标记为0
-                queryWrapper.eq("sg.goods_status", queryDTO.getGoodsStatus());
+                queryWrapper.eq("sg.goods_status", queryDTO.getGoodsStatus())
+                        .eq("sg.delete_flag", Constants.DeleteFlag.NOT_DELETED);
             }
         }
         

+ 56 - 8
alien-second/src/main/java/shop/alien/second/service/impl/SecondTradeRecordServiceImpl.java

@@ -10,6 +10,8 @@ import org.springframework.stereotype.Service;
 import org.springframework.transaction.annotation.Transactional;
 import shop.alien.entity.result.BusinessException;
 import shop.alien.entity.second.SecondGoods;
+import shop.alien.entity.second.SecondGoodsRecord;
+import shop.alien.entity.second.SecondTradeOperation;
 import shop.alien.entity.second.SecondTradeRecord;
 import shop.alien.entity.second.vo.SecondTradeRecordVo;
 import shop.alien.entity.store.LifeMessage;
@@ -20,6 +22,8 @@ import shop.alien.mapper.LifeMessageMapper;
 import shop.alien.mapper.LifeUserMapper;
 import shop.alien.mapper.StoreDictionaryMapper;
 import shop.alien.mapper.second.SecondGoodsMapper;
+import shop.alien.mapper.second.SecondGoodsRecordMapper;
+import shop.alien.mapper.second.SecondTradeOperationMapper;
 import shop.alien.mapper.second.SecondTradeRecordMapper;
 import shop.alien.second.feign.AlienStoreFeign;
 import shop.alien.second.service.SecondTradeRecordService;
@@ -46,7 +50,9 @@ import java.util.Objects;
 public class SecondTradeRecordServiceImpl extends ServiceImpl<SecondTradeRecordMapper, SecondTradeRecord> implements SecondTradeRecordService {
 
     private final SecondTradeRecordMapper secondTradeRecordMapper;
+    private final SecondTradeOperationMapper secondTradeOperationMapper;
     private final SecondGoodsMapper secondGoodsMapper;
+    private final SecondGoodsRecordMapper secondGoodsRecordMapper;
     private final LifeMessageMapper lifeMessageMapper;
     private final LifeUserMapper lifeUserMapper;
     private final AlienStoreFeign alienStoreFeign;
@@ -66,9 +72,24 @@ public class SecondTradeRecordServiceImpl extends ServiceImpl<SecondTradeRecordM
                 String tradeNo = "S" + now.toString().replace("-", "") + String.format("%05d", count + 1);
                 trade.setTradeNo(tradeNo);
             }
+            LambdaQueryWrapper<SecondGoodsRecord> goodsWrapper = new LambdaQueryWrapper<>();
+            goodsWrapper.eq(SecondGoodsRecord::getGoodsId, trade.getGoodsId());
+            goodsWrapper.eq(SecondGoodsRecord::getGoodsStatus, "3");
+            goodsWrapper.orderByDesc(SecondGoodsRecord::getCreatedTime);
+            goodsWrapper.last(" limit 1 ");
+            SecondGoodsRecord goodsRecord = secondGoodsRecordMapper.selectOne(goodsWrapper);
+            if (null != goodsRecord) trade.setGoodsRecordId(goodsRecord.getId());
             // 保存交易记录
             secondTradeRecordMapper.insert(trade);
 
+            // 保存交易操作表
+            SecondTradeOperation operation = new SecondTradeOperation();
+            operation.setTradeId(trade.getId());
+            operation.setUserId(Objects.requireNonNull(JwtUtil.getCurrentUserInfo()).getInteger("userId"));
+            operation.setType(1);
+            operation.setCreatedTime(new Date());
+            secondTradeOperationMapper.insert(operation);
+
             // 商品更新交易id
             SecondGoods goods = new SecondGoods();
             goods.setId(trade.getGoodsId());
@@ -177,15 +198,16 @@ public class SecondTradeRecordServiceImpl extends ServiceImpl<SecondTradeRecordM
             // 修改交易状态
             SecondTradeRecord tradeRecord = new SecondTradeRecord();
             tradeRecord.setId(tradeId);
-            if (type == 1) {
-                tradeRecord.setTradeStatus(3);
-                trade.setTradeStatus(3);
-            } else {
-                tradeRecord.setTradeStatus(2);
-                trade.setTradeStatus(2);
-            }
+            tradeRecord.setTradeStatus(type == 1 ? 3 : 2);
             secondTradeRecordMapper.updateById(tradeRecord);
 
+            // 保存交易操作表
+            SecondTradeOperation operation = new SecondTradeOperation();
+            operation.setTradeId(trade.getId());
+            operation.setUserId(Objects.requireNonNull(JwtUtil.getCurrentUserInfo()).getInteger("userId"));
+            operation.setType(type == 1 ? 3 : 2);
+            secondTradeOperationMapper.insert(operation);
+
             // 商品信息
             SecondGoods goods = secondGoodsMapper.selectById(trade.getGoodsId());
 
@@ -201,6 +223,7 @@ public class SecondTradeRecordServiceImpl extends ServiceImpl<SecondTradeRecordM
             lifeMessageMapper.updateById(message);
 
             // 发送消息
+            trade.setTradeStatus(type == 1 ? 3 : 2);
             sendMsg(goods, trade, trade.getTradeStatus(), "4");
 
             // 发起交易人信息
@@ -249,6 +272,14 @@ public class SecondTradeRecordServiceImpl extends ServiceImpl<SecondTradeRecordM
             tradeRecord.setCancelReasonSupplement(cancelReasonSupplement);
             secondTradeRecordMapper.updateById(tradeRecord);
 
+            // 保存交易操作表
+            SecondTradeOperation operation = new SecondTradeOperation();
+            operation.setTradeId(tradeId);
+            operation.setUserId(Objects.requireNonNull(JwtUtil.getCurrentUserInfo()).getInteger("userId"));
+            operation.setType(7);
+            operation.setCreatedTime(new Date());
+            secondTradeOperationMapper.insert(operation);
+
             // 交易信息
             SecondTradeRecord trade = secondTradeRecordMapper.selectById(tradeId);
 
@@ -316,7 +347,15 @@ public class SecondTradeRecordServiceImpl extends ServiceImpl<SecondTradeRecordM
             }
             secondTradeRecordMapper.updateById(record);
 
-            // 删除签到提醒
+            // 保存交易操作表
+            SecondTradeOperation operation = new SecondTradeOperation();
+            operation.setTradeId(tradeId);
+            operation.setUserId(userId);
+            operation.setType(4);
+            operation.setCreatedTime(new Date());
+            secondTradeOperationMapper.insert(operation);
+
+            // 删除签到提醒消息
             LifeMessage signInMessage = lifeMessageMapper.selectById(messageId);
             if (null == signInMessage) throw new BusinessException("该交易已签到,无需再次签到");
             lifeMessageMapper.deleteById(messageId);
@@ -409,6 +448,15 @@ public class SecondTradeRecordServiceImpl extends ServiceImpl<SecondTradeRecordM
                 return false;
             }
             secondTradeRecordMapper.updateById(record);
+
+            // 保存交易操作表
+            SecondTradeOperation operation = new SecondTradeOperation();
+            operation.setTradeId(tradeId);
+            operation.setUserId(userId);
+            operation.setType(1 == type ? 5 : 6);
+            operation.setCreatedTime(new Date());
+            secondTradeOperationMapper.insert(operation);
+
             return true;
         } catch (Exception e) {
             log.error("SecondTradeRecordServiceImpl.tradeCompleteConfirm(): Error Msg={}", e.getMessage());

+ 55 - 8
alien-second/src/main/java/shop/alien/second/task/Task.java

@@ -11,6 +11,7 @@ import org.springframework.scheduling.annotation.Scheduled;
 import org.springframework.stereotype.Component;
 import shop.alien.config.redis.BaseRedisService;
 import shop.alien.entity.second.SecondGoods;
+import shop.alien.entity.second.SecondTradeOperation;
 import shop.alien.entity.second.SecondTradeRecord;
 import shop.alien.entity.store.LifeMessage;
 import shop.alien.entity.store.LifeNotice;
@@ -20,6 +21,7 @@ import shop.alien.mapper.LifeMessageMapper;
 import shop.alien.mapper.LifeNoticeMapper;
 import shop.alien.mapper.LifeUserMapper;
 import shop.alien.mapper.second.SecondGoodsMapper;
+import shop.alien.mapper.second.SecondTradeOperationMapper;
 import shop.alien.mapper.second.SecondTradeRecordMapper;
 import shop.alien.second.feign.AlienStoreFeign;
 
@@ -28,6 +30,7 @@ import java.time.ZoneId;
 import java.util.ArrayList;
 import java.util.Date;
 import java.util.List;
+import java.util.stream.Collectors;
 
 @Slf4j
 @Component
@@ -48,6 +51,8 @@ public class Task {
 
     private final SecondGoodsMapper secondGoodsMapper;
 
+    private final SecondTradeOperationMapper secondTradeOperationMapper;
+
     @Value("${ScheduledTask.enabled}")
     private boolean isEnable;
 
@@ -284,24 +289,27 @@ public class Task {
 
         log.info("开始执行定时任务: 二手交易平台 - 交易超时未确认则自动取消 - secondTradeTimeoutCancel");
         try {
-            LocalDateTime now = LocalDateTime.now().withSecond(0).withNano(0);
+            Date now = Date.from(LocalDateTime.now().withSecond(0).withNano(0).atZone(ZoneId.systemDefault()).toInstant());
 
             // 查询所有待确认
             LambdaQueryWrapper<SecondTradeRecord> queryWrapper = new LambdaQueryWrapper<>();
             queryWrapper.eq(SecondTradeRecord::getTradeStatus, 1);
+            queryWrapper.eq(SecondTradeRecord::getTransactionTime, now);
             List<SecondTradeRecord> tradeRecordList = secondTradeRecordMapper.selectList(queryWrapper);
-            List<Integer> tradeIdList = new ArrayList<>();
-            for (SecondTradeRecord tradeRecord : tradeRecordList) {
-                LocalDateTime tenMinutesAgo = tradeRecord.getTransactionTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime().withSecond(0).withNano(0);
-                if (now.isEqual(tenMinutesAgo)) {
-                    tradeIdList.add(tradeRecord.getId());
-                }
-            }
+            List<Integer> tradeIdList = tradeRecordList.stream().map(SecondTradeRecord::getId).collect(Collectors.toList());
             if (CollectionUtil.isNotEmpty(tradeIdList)) {
                 LambdaUpdateWrapper<SecondTradeRecord> updateWrapper = new LambdaUpdateWrapper<>();
                 updateWrapper.in(SecondTradeRecord::getId, tradeIdList)
                         .set(SecondTradeRecord::getTradeStatus, 6);
                 secondTradeRecordMapper.update(null, updateWrapper);
+
+                for (Integer id : tradeIdList) {
+                    SecondTradeOperation operation = new SecondTradeOperation();
+                    operation.setTradeId(id);
+                    operation.setUserId(0);
+                    operation.setType(7);
+                    secondTradeOperationMapper.insert(operation);
+                }
             }
         } catch (Exception e) {
             log.error("SecondGoodsTradeXxlJob.secondTradeTimeoutCancel Error Mgs={}", e.getMessage());
@@ -309,6 +317,45 @@ public class Task {
     }
 
     /**
+     * 二手交易平台 - 到达交易时间12个小时后,自动交易失败
+     */
+    @Scheduled(cron = "0 * * * * ?")
+    private void secondTradeTimeoutFail() {
+        if (!isEnable) {
+            return;
+        }
+
+        log.info("开始执行定时任务: 二手交易平台 - 到达交易时间12个小时后,自动交易失败 - secondTradeTimeoutFail");
+        try {
+            Date twelveBefore = Date.from(LocalDateTime.now().plusHours(12).withSecond(0).withNano(0).atZone(ZoneId.systemDefault()).toInstant());
+
+            // 查询所有待确认
+            LambdaQueryWrapper<SecondTradeRecord> queryWrapper = new LambdaQueryWrapper<>();
+            queryWrapper.eq(SecondTradeRecord::getTradeStatus, 3);
+            queryWrapper.eq(SecondTradeRecord::getTransactionTime, twelveBefore);
+            List<SecondTradeRecord> tradeRecordList = secondTradeRecordMapper.selectList(queryWrapper);
+            List<Integer> tradeIdList = tradeRecordList.stream().map(SecondTradeRecord::getId).collect(Collectors.toList());
+            if (CollectionUtil.isNotEmpty(tradeIdList)) {
+                LambdaUpdateWrapper<SecondTradeRecord> updateWrapper = new LambdaUpdateWrapper<>();
+                updateWrapper.in(SecondTradeRecord::getId, tradeIdList)
+                        .set(SecondTradeRecord::getTradeStatus, 5);
+                secondTradeRecordMapper.update(null, updateWrapper);
+
+                for (Integer id : tradeIdList) {
+                    SecondTradeOperation operation = new SecondTradeOperation();
+                    operation.setTradeId(id);
+                    operation.setUserId(0);
+                    operation.setType(6);
+                    operation.setCreatedTime(new Date());
+                    secondTradeOperationMapper.insert(operation);
+                }
+            }
+        } catch (Exception e) {
+            log.error("SecondGoodsTradeXxlJob.secondTradeTimeoutFail Error Mgs={}", e.getMessage());
+        }
+    }
+
+    /**
      * 二手交易平台 - 每分钟从redis中读取已读的消息id 并将数据库设为已读
      */
     @Scheduled(cron = "0 * * * * ?")

+ 4 - 4
alien-store/src/main/java/shop/alien/store/controller/LifeCouponController.java

@@ -95,11 +95,11 @@ public class LifeCouponController {
     }
 
     @ApiOperation("核销订单前效验")
-    @ApiImplicitParams(@ApiImplicitParam(name = "orderId", value = "订单id", dataType = "Integer", paramType = "query", required = true))
+    @ApiImplicitParams(@ApiImplicitParam(name = "orderCode", value = "劵code", dataType = "String", paramType = "query", required = true))
     @GetMapping("/orderVerify")
-    public R<String> orderVerify(@RequestParam("orderId") Integer orderId) {
-        log.info("LifeCouponController.orderVerify?orderId={}", orderId);
-        return lifeCouponService.orderVerify(orderId);
+    public R<String> orderVerify(@RequestParam("orderCode") String orderCode) {
+        log.info("LifeCouponController.orderVerify?orderCode={}", orderCode);
+        return lifeCouponService.orderVerify(orderCode);
     }
 
     @ApiOperation("获取优惠券状态")

+ 1 - 1
alien-store/src/main/java/shop/alien/store/controller/ManagementInfoController.java

@@ -175,7 +175,7 @@ public class ManagementInfoController {
             @ApiImplicitParam(name = "page", value = "分页序数", dataType = "String", paramType = "query"),
             @ApiImplicitParam(name = "size", value = "分页长度", dataType = "String", paramType = "query"),
             @ApiImplicitParam(name = "type", value = "查询类型(1:当日,2:所有)", dataType = "String", paramType = "query"),
-            @ApiImplicitParam(name = "tabType", value = "订单类型(全部订单:1,待付款:2,已付款:3,已退款:4,已完成:5)", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "tabType", value = "订单类型(全部订单:1,待付款:2,待付款/已取消:3,已退款:4,已完成:5)", dataType = "String", paramType = "query"),
             @ApiImplicitParam(name = "orderId", value = "订单编号", dataType = "String", paramType = "query"),
             @ApiImplicitParam(name = "startTime", value = "开始时间", dataType = "String", paramType = "query"),
             @ApiImplicitParam(name = "entTime", value = "结束时间", dataType = "String", paramType = "query"),

+ 2 - 2
alien-store/src/main/java/shop/alien/store/service/LifeCouponService.java

@@ -52,8 +52,8 @@ public interface LifeCouponService extends IService<LifeCoupon> {
 
     /**
      * 核销订单前效验
-     * @param orderId
+     * @param orderCode
      * @return
      */
-    R<String> orderVerify(Integer orderId);
+    R<String> orderVerify(String orderCode);
 }

+ 174 - 76
alien-store/src/main/java/shop/alien/store/service/impl/LifeCouponServiceImpl.java

@@ -9,6 +9,7 @@ import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
 import lombok.RequiredArgsConstructor;
 import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
 import org.springframework.util.CollectionUtils;
 import org.springframework.util.StringUtils;
 import shop.alien.entity.result.R;
@@ -22,10 +23,7 @@ import shop.alien.util.common.UniqueRandomNumGenerator;
 
 import java.math.BigDecimal;
 import java.math.RoundingMode;
-import java.time.DayOfWeek;
-import java.time.LocalDate;
-import java.time.LocalDateTime;
-import java.time.ZoneId;
+import java.time.*;
 import java.time.format.DateTimeFormatter;
 import java.time.format.TextStyle;
 import java.util.*;
@@ -227,17 +225,28 @@ public class LifeCouponServiceImpl extends ServiceImpl<LifeCouponMapper, LifeCou
         return resultMap;
     }
 
+
     @Override
+    @Transactional(rollbackFor = Exception.class)
     public Map<String, String> newCouponVerify(String storeId, String quanCode) {
         Map<String, String> resultMap = new HashMap<>();
-        OrderCouponMiddle orderCouponMiddle = orderCouponMiddleMapper.selectOne(new LambdaQueryWrapper<OrderCouponMiddle>().eq(OrderCouponMiddle::getCouponCode,quanCode));
-        if(!StringUtils.isEmpty(orderCouponMiddle)){
-            LifeUserOrder lifeUserOrder = lifeUserOrderMapper.selectOne(new LambdaQueryWrapper<LifeUserOrder>().eq(LifeUserOrder::getId,orderCouponMiddle.getOrderId()));
+        OrderCouponMiddle orderCouponMiddle = orderCouponMiddleMapper.selectOne(new LambdaQueryWrapper<OrderCouponMiddle>().eq(OrderCouponMiddle::getCouponCode, quanCode));
+        if (!StringUtils.isEmpty(orderCouponMiddle)) {
+            LifeUserOrder lifeUserOrder = lifeUserOrderMapper.selectOne(new LambdaQueryWrapper<LifeUserOrder>().eq(LifeUserOrder::getId, orderCouponMiddle.getOrderId()));
             //CouponType 类型为 1:代金券 2:团购套餐
-            if(lifeUserOrder.getCouponType()==1){
+            if (lifeUserOrder.getCouponType() == 1) {
                 orderCouponMiddle.setStatus(2);
                 orderCouponMiddle.setUsedTime(new Date());
                 orderCouponMiddleMapper.updateById(orderCouponMiddle);
+                //通过订单id查询中间表 如果该订单下所有劵都为已核销状态更改订单表状态为已核销
+                List<OrderCouponMiddle> couponMiddleList = orderCouponMiddleMapper.selectList(new LambdaQueryWrapper<OrderCouponMiddle>()
+                        .eq(OrderCouponMiddle::getOrderId,lifeUserOrder.getId()));
+                boolean isExist =  couponMiddleList.stream()
+                        .allMatch(str -> str.getStatus()==2);
+                if(isExist){
+                    lifeUserOrder.setStatus(2);
+                    lifeUserOrderMapper.updateById(lifeUserOrder);
+                }
                 // TODO 抽成比例应该从商户里取
                 BigDecimal amounts = new BigDecimal(lifeUserOrder.getFinalPrice()).multiply(new BigDecimal(100));
                 BigDecimal commission = amounts.multiply(new BigDecimal(0.04)).setScale(0, RoundingMode.HALF_UP);
@@ -262,10 +271,20 @@ public class LifeCouponServiceImpl extends ServiceImpl<LifeCouponMapper, LifeCou
                 resultMap.put("code", "true");
                 resultMap.put("message", "核销成功");
 
-            }else if(lifeUserOrder.getCouponType()==2){
+            } else if (lifeUserOrder.getCouponType() == 2) {
                 orderCouponMiddle.setStatus(2);
                 orderCouponMiddle.setUsedTime(new Date());
                 orderCouponMiddleMapper.updateById(orderCouponMiddle);
+                //通过订单id查询中间表 如果该订单下所有劵都为已核销状态更改订单表状态为已核销
+                List<OrderCouponMiddle> couponMiddleList = orderCouponMiddleMapper.selectList(new LambdaQueryWrapper<OrderCouponMiddle>()
+                        .eq(OrderCouponMiddle::getOrderId,lifeUserOrder.getId()));
+                boolean isExist =  couponMiddleList.stream()
+                        .allMatch(str -> str.getStatus()==2);
+                if(isExist){
+                    lifeUserOrder.setStatus(2);
+                    lifeUserOrderMapper.updateById(lifeUserOrder);
+                }
+
                 // TODO 抽成比例应该从商户里取
                 BigDecimal amounts = new BigDecimal(lifeUserOrder.getFinalPrice()).multiply(new BigDecimal(100));
                 BigDecimal commission = amounts.multiply(new BigDecimal(0.04)).setScale(0, RoundingMode.HALF_UP);
@@ -290,6 +309,9 @@ public class LifeCouponServiceImpl extends ServiceImpl<LifeCouponMapper, LifeCou
                 resultMap.put("code", "true");
                 resultMap.put("message", "核销成功");
             }
+        } else {
+            resultMap.put("code", "false");
+            resultMap.put("message", "核销失败");
         }
         return resultMap;
     }
@@ -388,77 +410,23 @@ public class LifeCouponServiceImpl extends ServiceImpl<LifeCouponMapper, LifeCou
     /**
      * 核销订单前效验
      *
-     * @param orderId
+     * @param orderCode
      * @return
      */
     @Override
-    public R<String> orderVerify(Integer orderId) {
-            OrderCouponMiddle orderCouponMiddle = orderCouponMiddleMapper.selectOne(new LambdaQueryWrapper<OrderCouponMiddle>().eq(OrderCouponMiddle::getId, orderId));
-            if (!StringUtils.isEmpty(orderCouponMiddle) && orderCouponMiddle.getStatus() == 1) {
-                if (!StringUtils.isEmpty(orderCouponMiddle)) {
-                    LifeGroupBuyMain lifeGroupBuyMain = lifeGroupBuyMainMapper.selectOne(new LambdaQueryWrapper<LifeGroupBuyMain>().eq(LifeGroupBuyMain::getId, orderCouponMiddle.getCouponId()));
-                    //团购有效期类型为:0 指定天数
-                    if (lifeGroupBuyMain.getEffectiveDateType() == 0) {
-                        //订单支付时间加上指定天数 为团购劵有效期
-                        LifeUserOrder lifeUserOrder = lifeUserOrderMapper.selectOne(new LambdaQueryWrapper<LifeUserOrder>().eq(LifeUserOrder::getId, orderCouponMiddle.getOrderId()));
-                        LocalDate localDate = lifeUserOrder.getPayTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDate();
-                        LocalDate validityPeriod = localDate.plusDays(Long.parseLong(lifeGroupBuyMain.getEffectiveDateValue()));
-                        LocalDate nowDate = LocalDate.now(); // 获取当前时间
-                        if (nowDate.isAfter(validityPeriod)) {
-                            return R.fail("该劵不在有效期内");
-                        }
-                    } else if (lifeGroupBuyMain.getEffectiveDateType() == 1) {//类型为:1 指定时间段
-                        String[] strings = lifeGroupBuyMain.getEffectiveDateValue().split(",");
-                        String startDate = strings[0];
-                        String endDate = strings[1];
-                        LocalDate localStartDate = LocalDate.parse(startDate);
-                        LocalDate localEndDate = LocalDate.parse(endDate);
-                        LocalDate nowDate = LocalDate.now(); // 获取当前时间
-                        if (nowDate.isAfter(localEndDate) || nowDate.isBefore(localStartDate)) {
-                            return R.fail("该劵不在有效期内");
-                        }
-                    }
-                    //判断订单是否在不可用日期内
-                    //判断当前日期是否在不可用星期
-                    if(lifeGroupBuyMain.getDisableDateType() == 1){//限制日期: 1234567;节日id
-                        LocalDate nowDate = LocalDate.now(); // 获取当前时间
-                        DayOfWeek dayOfWeek = nowDate.getDayOfWeek();
-                        String week = dayOfWeek.getDisplayName(TextStyle.FULL, Locale.CHINA);
-                        String beforeSemicolon = lifeGroupBuyMain.getDisableDateValue().split(";")[0];
-                        if (!StringUtils.isEmpty(beforeSemicolon)) {
-                            List<String> collectUnavailableDate = Arrays.stream(beforeSemicolon.split(",")).map(String::trim).collect(Collectors.toList());
-                            boolean isExist = collectUnavailableDate.stream().anyMatch(s -> s.equals(week));
-                            if(isExist){
-                                return R.fail("该劵在不可用日期内");
-                            }
-                        }
-                        //判断当前日期是否在不可用节日
-                        String [] strings = lifeGroupBuyMain.getDisableDateValue().split(";");
-                        if(strings.length>1){
-                                String afterSemicolon = lifeGroupBuyMain.getDisableDateValue().split(";")[1];
-                                List<String> collectUnavailableDate = Arrays.stream(afterSemicolon.split(",")).map(String::trim).collect(Collectors.toList());
-                                List<EssentialHolidayComparison> essentialHolidayComparisons = essentialHolidayComparisonMapper.
-                                        selectList(new LambdaQueryWrapper<EssentialHolidayComparison>().in(EssentialHolidayComparison::getId, collectUnavailableDate));
-                                boolean isExist = essentialHolidayComparisons.stream().anyMatch(s -> nowDate.isAfter(s.getStartTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDate())
-                                        && nowDate.isBefore(s.getEndTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDate()));
-                                if(isExist){
-                                    return R.fail("该劵在不可用日期内");
-                                }
-                        }
-                    }
-                    //判断当前日期是否在自定义不可用日期内
-                    if(lifeGroupBuyMain.getDisableDateType() == 2){
-                        String [] customDate = lifeGroupBuyMain.getDisableDateValue().split(";");
-                        boolean isExist = isCurrentDateInAnyRange(customDate);
-                        if(isExist){
-                            return R.fail("该劵在不可用日期内");
-                        }
-                    }
-                }
-            }else{
-                return R.fail("该劵不是待使用状态");
+    public R<String> orderVerify(String orderCode) {
+        OrderCouponMiddle orderCouponMiddle = orderCouponMiddleMapper.selectOne(new LambdaQueryWrapper<OrderCouponMiddle>().eq(OrderCouponMiddle::getCouponCode, orderCode));
+        if (!StringUtils.isEmpty(orderCouponMiddle) && orderCouponMiddle.getStatus() == 1) {
+            LifeUserOrder lifeUserOrder = lifeUserOrderMapper.selectOne(new LambdaQueryWrapper<LifeUserOrder>().eq(LifeUserOrder::getId, orderCouponMiddle.getOrderId()));
+            //类型为:1 代金券订单
+            if (lifeUserOrder.getCouponType() == 1) {
+                return couponVerification(orderCouponMiddle);
+            } else if (lifeUserOrder.getCouponType() == 2) {//类型为:2 团购订单
+                return groupVerification(orderCouponMiddle);
             }
-        return R.success("效验通过");
+        }
+        return R.fail("该劵不是待使用状态");
+
     }
 
     public static boolean isCurrentDateInAnyRange(String[] dateRanges) {
@@ -494,4 +462,134 @@ public class LifeCouponServiceImpl extends ServiceImpl<LifeCouponMapper, LifeCou
         return false;
     }
 
+    public R<String> groupVerification(OrderCouponMiddle orderCouponMiddle) {
+        LifeGroupBuyMain lifeGroupBuyMain = lifeGroupBuyMainMapper.selectOne(new LambdaQueryWrapper<LifeGroupBuyMain>().eq(LifeGroupBuyMain::getId, orderCouponMiddle.getCouponId()));
+        //团购有效期类型为:0 指定天数
+        if (lifeGroupBuyMain.getEffectiveDateType() == 0) {
+            //订单支付时间加上指定天数 为团购劵有效期
+            LifeUserOrder lifeUserOrder = lifeUserOrderMapper.selectOne(new LambdaQueryWrapper<LifeUserOrder>().eq(LifeUserOrder::getId, orderCouponMiddle.getOrderId()));
+            LocalDate localDate = lifeUserOrder.getPayTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDate();
+            LocalDate validityPeriod = localDate.plusDays(Long.parseLong(lifeGroupBuyMain.getEffectiveDateValue()));
+            LocalDate nowDate = LocalDate.now(); // 获取当前时间
+            if (nowDate.isAfter(validityPeriod)) {
+                return R.fail("该劵不在有效期内");
+            }
+        } else if (lifeGroupBuyMain.getEffectiveDateType() == 1) {//类型为:1 指定时间段
+            String[] strings = lifeGroupBuyMain.getEffectiveDateValue().split(",");
+            String startDate = strings[0];
+            String endDate = strings[1];
+            LocalDate localStartDate = LocalDate.parse(startDate);
+            LocalDate localEndDate = LocalDate.parse(endDate);
+            LocalDate nowDate = LocalDate.now(); // 获取当前时间
+            if (nowDate.isAfter(localEndDate) || nowDate.isBefore(localStartDate)) {
+                return R.fail("该劵不在有效期内");
+            }
+        }
+        //判断订单是否在不可用日期内
+        //判断当前日期是否在不可用星期
+        if (lifeGroupBuyMain.getDisableDateType() == 1) {//限制日期: 1234567;节日id
+            LocalDate nowDate = LocalDate.now(); // 获取当前时间
+            DayOfWeek dayOfWeek = nowDate.getDayOfWeek();
+            String week = dayOfWeek.getDisplayName(TextStyle.FULL, Locale.CHINA);
+            String beforeSemicolon = lifeGroupBuyMain.getDisableDateValue().split(";")[0];
+            if (!StringUtils.isEmpty(beforeSemicolon)) {
+                List<String> collectUnavailableDate = Arrays.stream(beforeSemicolon.split(",")).map(String::trim).collect(Collectors.toList());
+                boolean isExist = collectUnavailableDate.stream().anyMatch(s -> s.equals(week));
+                if (isExist) {
+                    return R.fail("该劵在不可用日期内");
+                }
+            }
+            //判断当前日期是否在不可用节日
+            String[] strings = lifeGroupBuyMain.getDisableDateValue().split(";");
+            if (strings.length > 1) {
+                String afterSemicolon = lifeGroupBuyMain.getDisableDateValue().split(";")[1];
+                List<String> collectUnavailableDate = Arrays.stream(afterSemicolon.split(",")).map(String::trim).collect(Collectors.toList());
+                List<EssentialHolidayComparison> essentialHolidayComparisons = essentialHolidayComparisonMapper.
+                        selectList(new LambdaQueryWrapper<EssentialHolidayComparison>().in(EssentialHolidayComparison::getId, collectUnavailableDate));
+                boolean isExist = essentialHolidayComparisons.stream().anyMatch(s -> !nowDate.isBefore(s.getStartTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDate())
+                        && !nowDate.isAfter(s.getEndTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDate()));
+                if (isExist) {
+                    return R.fail("该劵在不可用日期内");
+                }
+            }
+        }
+        //判断当前日期是否在自定义不可用日期内
+        if (lifeGroupBuyMain.getDisableDateType() == 2) {
+            String[] customDate = lifeGroupBuyMain.getDisableDateValue().split(";");
+            boolean isExist = isCurrentDateInAnyRange(customDate);
+            if (isExist) {
+                return R.fail("该劵在不可用日期内");
+            }
+        }
+        return R.success("效验通过");
+    }
+
+    public R<String> couponVerification(OrderCouponMiddle orderCouponMiddle) {
+        LifeCoupon lifeCoupon = lifeCouponMapper.selectOne(new LambdaQueryWrapper<LifeCoupon>().eq(LifeCoupon::getId, orderCouponMiddle.getCouponId()));
+        //代金券有效期类型为:1 指定天数
+        if (lifeCoupon.getExpirationType().equals("1")) {
+            //订单支付时间加上指定天数 为团购劵有效期
+            LifeUserOrder lifeUserOrder = lifeUserOrderMapper.selectOne(new LambdaQueryWrapper<LifeUserOrder>().eq(LifeUserOrder::getId, orderCouponMiddle.getOrderId()));
+            LocalDate localDate = lifeUserOrder.getPayTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDate();
+            LocalDate validityPeriod = localDate.plusDays(lifeCoupon.getExpirationDate());
+            LocalDate nowDate = LocalDate.now(); // 获取当前时间
+            if (nowDate.isAfter(validityPeriod)) {
+                return R.fail("该劵不在有效期内");
+            }
+        } else if (lifeCoupon.getExpirationType().equals("2")) {//类型为:2 指定时间段
+            String[] strings = lifeCoupon.getValidityPeriod() .split(",");
+            long start = Long.parseLong(strings[0]);
+            long end = Long.parseLong(strings[1]);
+            LocalDate startDate = Instant.ofEpochMilli(start)
+                    .atZone(ZoneId.systemDefault())
+                    .toLocalDate();
+            LocalDate endDate = Instant.ofEpochMilli(end)
+                    .atZone(ZoneId.systemDefault())
+                    .toLocalDate();
+            LocalDate nowDate = LocalDate.now(); // 获取当前时间
+            if (nowDate.isAfter(endDate) || nowDate.isBefore(startDate)) {
+                return R.fail("该劵不在有效期内");
+            }
+        }
+
+        //判断代金券订单是否在不可用日期内
+        //判断当前日期是否在不可用星期
+        if (lifeCoupon.getUnusedType().equals("2")) {//限制日期: 1234567;节日id
+            LocalDate nowDate = LocalDate.now(); // 获取当前时间
+            DayOfWeek dayOfWeek = nowDate.getDayOfWeek();
+            String week = dayOfWeek.getDisplayName(TextStyle.FULL, Locale.CHINA);
+            String beforeSemicolon = lifeCoupon.getUnavaiLableDate().split(";")[0];
+            if (!StringUtils.isEmpty(beforeSemicolon)) {
+                List<String> collectUnavailableDate = Arrays.stream(beforeSemicolon.split(",")).map(String::trim).collect(Collectors.toList());
+                boolean isExist = collectUnavailableDate.stream().anyMatch(s -> s.equals(week));
+                if (isExist) {
+                    return R.fail("该劵在不可用日期内");
+                }
+            }
+
+            //判断当前日期是否在不可用节日
+            String[] strings = lifeCoupon.getUnavaiLableDate().split(";");
+            if (strings.length > 1) {
+                String afterSemicolon = lifeCoupon.getUnavaiLableDate().split(";")[1];
+                List<String> collectUnavailableDate = Arrays.stream(afterSemicolon.split(",")).map(String::trim).collect(Collectors.toList());
+                List<EssentialHolidayComparison> essentialHolidayComparisons = essentialHolidayComparisonMapper.
+                        selectList(new LambdaQueryWrapper<EssentialHolidayComparison>().in(EssentialHolidayComparison::getId, collectUnavailableDate));
+                boolean isExist = essentialHolidayComparisons.stream().anyMatch(s -> !nowDate.isBefore(s.getStartTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDate())
+                        && !nowDate.isAfter(s.getEndTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDate()));
+                if (isExist) {
+                    return R.fail("该劵在不可用日期内");
+                }
+            }
+        }
+        //判断当前日期是否在自定义不可用日期内
+        if (lifeCoupon.getUnusedType().equals("3")) {
+            String[] customDate = lifeCoupon.getUnavaiLableDate().split(";");
+            boolean isExist = isCurrentDateInAnyRange(customDate);
+            if (isExist) {
+                return R.fail("该劵在不可用日期内");
+            }
+        }
+        return R.success("效验通过");
+    }
+
 }

+ 8 - 5
alien-store/src/main/java/shop/alien/store/service/impl/ManagementInfoServiceImpl.java

@@ -482,14 +482,17 @@ public class ManagementInfoServiceImpl implements ManagementInfoService {
         //转换一下订单类型 订单状态,0.待使用, 1.已核销, 2.已过期, 3.待退款,4.已退款,99.待付款,1:已取消
         String orderTypeQuery = "";
         if ("2".equals(orderType)) {
-            //todo 此时待付款状态还未有
-            orderTypeQuery = "99";
+            //待付款和已取消的数据
+            orderTypeQuery = "2";
         } else if ("3".equals(orderType)) {
-            orderTypeQuery = "0";
+            //已付款数据
+            orderTypeQuery = "1";
         } else if ("4".equals(orderType)) {
-            orderTypeQuery = "4";
+            // 已退款数据
+            orderTypeQuery = "5";
         } else if ("5".equals(orderType)) {
-            orderTypeQuery = "1";
+            // 已完成数据
+            orderTypeQuery = "7";
         } else if ("6".equals(orderType)) {
             orderTypeQuery = "3";
         }

+ 2 - 2
alien-store/src/main/java/shop/alien/store/service/impl/StoreCommentServiceImpl.java

@@ -575,9 +575,9 @@ public class StoreCommentServiceImpl extends ServiceImpl<StoreCommentMapper, Sto
             storeComment.setCreatedUserId(storeComment.getUserId());
 
             int i = this.save(storeComment) ? 0 : 1;
-
             Map<String, String> commentCountAndScore = storeCommentMapper.getCommentCountAndScoreInfo(storeId);
-            double total = StringUtils.isNotEmpty(commentCountAndScore.get("total")) ? Double.parseDouble(commentCountAndScore.get("total")) : 0;
+            String totalStr = String.valueOf(commentCountAndScore.get("total"));
+            double total = StringUtils.isNotEmpty(totalStr) ? Double.parseDouble(totalStr) : 0;
             double scoreAvg = StringUtils.isNotEmpty(commentCountAndScore.get("score")) ? Double.parseDouble(commentCountAndScore.get("score")) / total : 0;
             double tasteScore = StringUtils.isNotEmpty(commentCountAndScore.get("tasteScore")) ? Double.parseDouble(commentCountAndScore.get("tasteScore")) / total : 0;
             double enScore = StringUtils.isNotEmpty(commentCountAndScore.get("enScore")) ? Double.parseDouble(commentCountAndScore.get("enScore")) / total : 0;

+ 6 - 0
alien-store/src/main/java/shop/alien/store/service/impl/StoreInfoServiceImpl.java

@@ -557,6 +557,12 @@ public class StoreInfoServiceImpl extends ServiceImpl<StoreInfoMapper, StoreInfo
         String userAccount = storeInfoDto.getUserAccount();
         StoreUser storeUser = storeUserMapper.selectById(userAccount);
         storeUser.setStoreId(storeInfo.getId());
+        if(StringUtils.isNotEmpty(storeInfoDto.getStoreContact())){
+            storeUser.setName(storeInfoDto.getStoreContact());
+        }
+        if(StringUtils.isNotEmpty(storeInfoDto.getIdCard())){
+            storeUser.setIdCard(storeInfoDto.getIdCard());
+        }
         storeUserMapper.updateById(storeUser);
         //存入店铺营业执照图片
         List<String> businessLicenseAddress = storeInfoDto.getBusinessLicenseAddress();

+ 5 - 0
alien-util/src/main/java/shop/alien/util/common/Constants.java

@@ -23,6 +23,11 @@ public class Constants {
          * 二手商品图片类型
          */
         public static final Integer SECOND_HAND_GOODS = 18;
+        
+        /**
+         * 二手商品记录图片类型
+         */
+        public static final Integer SECOND_HAND_RECORD = 23;
     }
     
     /**