瀏覽代碼

直播间商品管理,直播间消息记录和在线离线和禁言

yuhongqi 6 天之前
父節點
當前提交
6447ae337f

+ 19 - 0
fs-common/src/main/java/com/fs/common/core/redis/RedisCache.java

@@ -305,5 +305,24 @@ public class RedisCache
         return redisTemplate.keys(pattern);
     }
 
+    /**
+     * 将对象添加到 Redis 的 Set 集合中
+     *
+     * @param key   Redis Key
+     * @param value 要添加的对象(例如 userId)
+     */
+    public void setSetCacheObject(String key, Object value) {
+        redisTemplate.opsForSet().add(key, value);
+    }
+
+    /**
+     * 从 Redis 的 Set 集合中移除指定的对象
+     *
+     * @param key   Redis Key
+     * @param value 要移除的对象(例如 userId)
+     */
+    public void removeSetCacheObject(String key, Object value) {
+        redisTemplate.opsForSet().remove(key, value);
+    }
 
 }

+ 4 - 2
fs-company/src/main/java/com/fs/company/controller/live/LiveGoodsController.java

@@ -11,6 +11,7 @@ import com.fs.framework.security.LoginUser;
 import com.fs.framework.security.SecurityUtils;
 import com.fs.live.domain.LiveGoods;
 import com.fs.live.service.ILiveGoodsService;
+import com.fs.live.vo.LiveGoodsVo;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.security.access.prepost.PreAuthorize;
 import org.springframework.web.bind.annotation.*;
@@ -36,13 +37,14 @@ public class LiveGoodsController extends BaseController
      */
     @PreAuthorize("@ss.hasPermi('live:liveGoods:list')")
     @GetMapping("/list")
-    public TableDataInfo list(LiveGoods liveGoods)
+    public TableDataInfo list(LiveGoods liveGoods, @RequestParam(value = "liveId", required = true) Long liveId)
     {
         // 设置企业ID和企业用户ID
         setCompanyId(liveGoods);
+        liveGoods.setLiveId(liveId);
 
         startPage();
-        List<LiveGoods> list = liveGoodsService.selectLiveGoodsList(liveGoods);
+        List<LiveGoodsVo> list = liveGoodsService.selectProductListByLiveId(liveGoods);
         return getDataTable(list);
     }
 

+ 2 - 1
fs-company/src/main/java/com/fs/company/controller/store/FsStoreProductController.java

@@ -45,9 +45,10 @@ public class FsStoreProductController extends BaseController
      */
 
     @GetMapping("/list")
-    public TableDataInfo list(FsStoreProduct fsStoreProduct)
+    public TableDataInfo list(FsStoreProduct fsStoreProduct, @RequestParam(required = false) String liveId)
     {
         startPage();
+        fsStoreProduct.setLiveId(liveId);
         List<FsStoreProductVO> list = fsStoreProductService.selectFsStoreProductListVO(fsStoreProduct);
         return getDataTable(list);
     }

+ 3 - 3
fs-live-app/src/main/java/com/fs/app/controller/LiveController.java

@@ -68,9 +68,9 @@ public class LiveController extends AppBaseController {
 			long seconds = live.getStartTime().until(now, ChronoUnit.SECONDS);
 			liveVo.setNowDuration(seconds);
 		}
-		if(liveVo.getNowDuration() != null){
-			liveVo.setNowPri(BigDecimal.valueOf(liveVo.getDuration()).divide(BigDecimal.valueOf(liveVo.getNowDuration()), 20, RoundingMode.UP));
-		}
+//		if(liveVo.getNowDuration() != null){
+//			liveVo.setNowPri(BigDecimal.valueOf(liveVo.getDuration()).divide(BigDecimal.valueOf(liveVo.getNowDuration()), 20, RoundingMode.UP));
+//		}
 		return R.ok().put("data", liveVo);
 	}
 

+ 2 - 7
fs-live-app/src/main/java/com/fs/app/websocket/service/WebSocketServer.java

@@ -73,7 +73,7 @@ public class WebSocketServer {
                 throw new BaseException("用户信息错误");
             }
 
-            liveWatchUserService.join(liveId, userId);
+            LiveWatchUser liveWatchUserVO = liveWatchUserService.join(liveId, userId);
             room.put(userId, session);
             // 直播间浏览量 +1
             redisCache.increment(PAGE_VIEWS_KEY + liveId, 1);
@@ -93,7 +93,6 @@ public class WebSocketServer {
             // 判断是否是该直播间的首次访客(独立访客统计)
             boolean isFirstVisit = redisCache.setIfAbsent(USER_VISIT_KEY + userId, 1, 1, TimeUnit.DAYS);
             if (isFirstVisit) {
-
                 redisCache.increment(UNIQUE_VISITORS_KEY + liveId, 1);
             }
 
@@ -103,8 +102,6 @@ public class WebSocketServer {
                 redisCache.increment(UNIQUE_VIEWERS_KEY + liveId, 1);
             }
 
-            LiveWatchUserVO liveWatchUserVO = liveWatchUserService.selectWatchUserByLiveIdAndUserId(liveId, userId);
-
             SendMsgVo sendMsgVo = new SendMsgVo();
             sendMsgVo.setLiveId(liveId);
             sendMsgVo.setUserId(userId);
@@ -141,14 +138,13 @@ public class WebSocketServer {
                 throw new BaseException("用户信息错误");
             }
 
-            liveWatchUserService.close(liveId, userId);
+            LiveWatchUser liveWatchUserVO = liveWatchUserService.close(liveId, userId);
             room.remove(userId);
 
             if (room.isEmpty()) {
                 rooms.remove(liveId);
             }
 
-            LiveWatchUserVO liveWatchUserVO = liveWatchUserService.selectWatchUserByLiveIdAndUserId(liveId, userId);
 
             // 直播间在线人数 -1
             redisCache.increment(ONLINE_USERS_KEY + liveId, -1);
@@ -202,7 +198,6 @@ public class WebSocketServer {
                             sendMessage(session, JSONObject.toJSONString(R.error("你已被禁言")));
                             return;
                         }
-
                         liveMsgService.save(liveMsg);
                     }
 

+ 5 - 0
fs-service/src/main/java/com/fs/his/domain/FsStoreProduct.java

@@ -1,6 +1,8 @@
 package com.fs.his.domain;
 
 import java.math.BigDecimal;
+
+import com.baomidou.mybatisplus.annotation.TableField;
 import com.fs.common.annotation.Excel;
 import com.fs.common.core.domain.BaseEntity;
 import io.swagger.models.auth.In;
@@ -235,4 +237,7 @@ public class FsStoreProduct extends BaseEntity {
     @Excel(name = "运费模板")
     private Long tempId;
     private Integer isDrug;
+
+    @TableField(exist = false)
+    private String liveId;
 }

+ 33 - 0
fs-service/src/main/java/com/fs/his/mapper/FsStoreProductMapper.java

@@ -6,6 +6,7 @@ import com.fs.his.domain.FsStoreProductRule;
 import com.fs.his.param.FsProductAttrValueParam;
 import com.fs.his.param.FsStoreProductListSParam;
 import com.fs.his.vo.*;
+import com.fs.live.domain.LiveGoods;
 import org.apache.ibatis.annotations.Param;
 import org.apache.ibatis.annotations.Select;
 import org.apache.ibatis.annotations.Update;
@@ -259,4 +260,36 @@ public interface FsStoreProductMapper {
     int updateStoreProductStock(@Param("productId") Long productId, @Param("stock") Integer stock);
 
 
+    List<FsStoreProduct> selectFsStoreProductByProductIds(@Param("productIdList") List<String> productIdList);
+
+    @Select({"<script> " +
+            "select p.*,pc.cate_name,st.store_name  from fs_store_product p left join fs_store_product_category pc on p.cate_id=pc.cate_id LEFT JOIN fs_store st ON st.store_id=p.store_id  " +
+            "where 1=1 " +
+            "<if test = 'maps.productName != null and  maps.productName !=\"\"    '> " +
+            "and p.product_name like CONCAT('%',#{maps.productName},'%') " +
+            "</if>" +
+            "<if test = 'maps.cateId != null    '> " +
+            "and (pc.cate_id =#{maps.cateId} or pc.pid=#{maps.cateId} )" +
+            "</if>" +
+            "<if test = 'maps.productType != null    '> " +
+            "and p.product_type =#{maps.productType} " +
+            "</if>" +
+            "<if test = 'maps.isShow != null    '> " +
+            "and p.is_show =#{maps.isShow} " +
+            "</if>" +
+            "<if test = 'maps.storeId != null    '> " +
+            "and p.store_id =#{maps.storeId} " +
+            "</if>" +
+            "<if test = 'maps.barCode != null    '> " +
+            "and p.product_id in(SELECT product_id FROM fs_store_product_attr_value WHERE bar_code =#{maps.barCode}) " +
+            "</if>" +
+            "<if test='ids != null and !ids.isEmpty()'> " +
+            "AND p.product_id NOT IN " +
+            "<foreach collection='ids' item='id' open='(' separator=',' close=')'> " +
+            "          #{id} " +
+            "</foreach> " +
+            "</if>"+
+            " order by p.product_id desc " +
+            "</script>"})
+    List<FsStoreProductVO> selectFsStoreProductListEx(@Param("maps") FsStoreProduct fsStoreProduct,@Param("ids")  List<String> exceptionProductIds);
 }

+ 10 - 0
fs-service/src/main/java/com/fs/his/service/impl/FsStoreProductServiceImpl.java

@@ -33,6 +33,7 @@ import com.fs.his.param.FsStoreProductListSParam;
 import com.fs.his.service.IFsPackageService;
 import com.fs.his.utils.ConfigUtil;
 import com.fs.his.vo.*;
+import com.fs.live.mapper.LiveGoodsMapper;
 import org.apache.commons.lang3.StringUtils;
 import org.springframework.beans.BeanUtils;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -62,6 +63,9 @@ public class FsStoreProductServiceImpl implements IFsStoreProductService {
     @Autowired
     private FsPackageOrderMapper fsPackageOrderMapper;
 
+    @Autowired
+    private LiveGoodsMapper liveGoodsMapper;
+
     @Autowired
     IFsPackageService fsPackageService;
     @Autowired
@@ -148,6 +152,12 @@ public class FsStoreProductServiceImpl implements IFsStoreProductService {
 
     @Override
     public List<FsStoreProductVO> selectFsStoreProductListVO(FsStoreProduct fsStoreProduct) {
+
+        if (StringUtils.isNotEmpty(fsStoreProduct.getLiveId())) {
+            List<String> exceptionProductIds = liveGoodsMapper.selectProductIdsByLiveId(Long.valueOf(fsStoreProduct.getLiveId()));
+            return fsStoreProductMapper.selectFsStoreProductListEx(fsStoreProduct, exceptionProductIds);
+        }
+
         return fsStoreProductMapper.selectFsStoreProductListVO(fsStoreProduct);
     }
 

+ 27 - 0
fs-service/src/main/java/com/fs/live/mapper/LiveGoodsMapper.java

@@ -2,7 +2,10 @@ package com.fs.live.mapper;
 
 import java.util.List;
 import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.fs.his.domain.FsStoreProduct;
 import com.fs.live.domain.LiveGoods;
+import com.fs.live.vo.LiveGoodsVo;
+import org.apache.ibatis.annotations.Param;
 
 /**
  * 直播商品Mapper接口
@@ -60,4 +63,28 @@ public interface LiveGoodsMapper extends BaseMapper<LiveGoods>{
     int deleteLiveGoodsByGoodsIds(Long[] goodsIds);
 
     Long selectStoreIdByLiveId(Long liveId);
+
+    /**
+     * 新增直播商品
+     *
+     * @param liveGoodsList 直播商品
+     * @return 结果
+     */
+    int insertLiveGoodsList(@Param("liveGoodsList") List<LiveGoods> liveGoodsList);
+
+    /**
+     * 批量查询商品ID
+     *
+     * @param liveId 直播ID
+     * @return 商品ID集合
+     */
+    List<String> selectProductIdsByLiveId(@Param("liveId") Long liveId);
+
+    /**
+     * 批量查询商品信息
+     *
+     * @param liveGoods 直播商品
+     * @return 商品信息集合
+     */
+    List<LiveGoodsVo> selectProductListByLiveId(LiveGoods liveGoods);
 }

+ 10 - 0
fs-service/src/main/java/com/fs/live/service/ILiveGoodsService.java

@@ -6,7 +6,9 @@ import java.util.Map;
 import com.baomidou.mybatisplus.extension.service.IService;
 import com.fs.company.domain.CompanyUser;
 import com.fs.his.domain.FsStore;
+import com.fs.his.domain.FsStoreProduct;
 import com.fs.live.domain.LiveGoods;
+import com.fs.live.vo.LiveGoodsVo;
 
 /**
  * 直播商品Service接口
@@ -72,4 +74,12 @@ public interface ILiveGoodsService extends IService<LiveGoods>{
     int insertLiveGoods(Map<String, Object> payload, CompanyUser user);
 
     FsStore getStoreByLiveId(Long liveId);
+
+    /**
+     * 查询直播商品列表
+     *
+     * @param liveGoods 直播商品
+     * @return 直播商品集合
+     */
+    List<LiveGoodsVo> selectProductListByLiveId(LiveGoods liveGoods);
 }

+ 2 - 2
fs-service/src/main/java/com/fs/live/service/ILiveWatchUserService.java

@@ -73,8 +73,8 @@ public interface ILiveWatchUserService extends IService<LiveWatchUser>{
 
     LiveWatchUser getByLiveIdAndUserId(long liveId, long userId);
 
-    void join(long liveId, long userId);
-    void close(long liveId, long userId);
+    LiveWatchUser join(long liveId, long userId);
+    LiveWatchUser close(long liveId, long userId);
 
     /**
      * 查询直播间在线用户列表

+ 38 - 6
fs-service/src/main/java/com/fs/live/service/impl/LiveGoodsServiceImpl.java

@@ -1,14 +1,16 @@
 package com.fs.live.service.impl;
 
-import java.util.List;
-import java.util.Map;
+import java.util.*;
+import java.util.stream.Collectors;
 
 import com.fs.common.utils.DateUtils;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
 import com.fs.company.domain.CompanyUser;
+import com.fs.his.domain.FsStoreProduct;
 import com.fs.his.mapper.FsStoreProductMapper;
 import com.fs.his.domain.FsStore;
 import com.fs.his.service.IFsStoreService;
+import com.fs.live.vo.LiveGoodsVo;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 import com.fs.live.mapper.LiveGoodsMapper;
@@ -113,6 +115,11 @@ public class LiveGoodsServiceImpl extends ServiceImpl<LiveGoodsMapper, LiveGoods
         return fsStoreService.selectFsStoreByStoreId(storeId);
     }
 
+    @Override
+    public List<LiveGoodsVo> selectProductListByLiveId(LiveGoods liveGoods) {
+        return baseMapper.selectProductListByLiveId(liveGoods);
+    }
+
     /**
      * 批量新增直播商品
      *
@@ -121,9 +128,34 @@ public class LiveGoodsServiceImpl extends ServiceImpl<LiveGoodsMapper, LiveGoods
      */
     @Override
     public int insertLiveGoods(Map<String, Object> payload, CompanyUser user) {
-        String liveId = (String) payload.get("liveId");
-        String goodsIds = (String) payload.get("goodsIds");
-//        fsStoreProductMapper.se
-        return 0;
+        Long liveId = Long.valueOf((String) payload.get("liveId"));
+        String productsId = (String) payload.get("productsId");
+        List<String> productIdList = new ArrayList<>(Arrays.asList(productsId.split(",")));
+        if (productIdList.isEmpty()) {
+            return 0;
+        }
+        //  查询商品信息列表(假设返回 List<StoreProduct>)
+        List<FsStoreProduct> productInfoList = fsStoreProductMapper.selectFsStoreProductByProductIds(productIdList);
+
+        //  转换为 LiveGoods 并批量插入
+        List<LiveGoods> liveGoodsList = productInfoList.stream()
+                .map(product -> {
+                    LiveGoods liveGoods = new LiveGoods();
+                    liveGoods.setLiveId(liveId);
+                    liveGoods.setCompanyId(user.getCompanyId());
+                    liveGoods.setCompanyUserId(user.getUserId());
+                    liveGoods.setStoreId(product.getStoreId());
+                    liveGoods.setProductId(product.getProductId());
+                    liveGoods.setStatus(1);
+                    liveGoods.setStock(Long.valueOf(product.getStock()));
+                    liveGoods.setSort(product.getSort());
+                    liveGoods.setCreateTime(DateUtils.getNowDate());
+                    liveGoods.setCreateBy(String.valueOf(user.getUserId()));
+                    return liveGoods;
+                })
+                .collect(Collectors.toList());
+//
+//        // 批量插入
+        return baseMapper.insertLiveGoodsList(liveGoodsList);
     }
 }

+ 13 - 2
fs-service/src/main/java/com/fs/live/service/impl/LiveWatchUserServiceImpl.java

@@ -2,11 +2,13 @@ package com.fs.live.service.impl;
 
 import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.fs.common.core.redis.RedisCache;
 import com.fs.common.utils.DateUtils;
 import com.fs.live.domain.LiveWatchUser;
 import com.fs.live.mapper.LiveWatchUserMapper;
 import com.fs.live.service.ILiveWatchUserService;
 import com.fs.live.vo.LiveWatchUserVO;
+import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
 import java.util.List;
@@ -22,6 +24,9 @@ import java.util.Objects;
 @Service
 public class LiveWatchUserServiceImpl extends ServiceImpl<LiveWatchUserMapper, LiveWatchUser> implements ILiveWatchUserService {
 
+    @Autowired
+    private RedisCache redisCache;
+
     /**
      * 查询直播间观看用户
      *
@@ -115,24 +120,30 @@ public class LiveWatchUserServiceImpl extends ServiceImpl<LiveWatchUserMapper, L
     }
 
     @Override
-    public void join(long liveId, long userId) {
+    public LiveWatchUser join(long liveId, long userId) {
         LiveWatchUser liveWatchUser = getByLiveIdAndUserId(liveId, userId);
         if(liveWatchUser != null) {
             liveWatchUser.setUpdateTime(DateUtils.getNowDate());
             liveWatchUser.setOnline(0);
+            liveWatchUser.setUpdateTime(DateUtils.getNowDate());
         }else{
             liveWatchUser = new LiveWatchUser();
             liveWatchUser.setLiveId(liveId);
             liveWatchUser.setUserId(userId);
+            liveWatchUser.setMsgStatus(0);
+            liveWatchUser.setOnline(0);
+            liveWatchUser.setCreateTime(DateUtils.getNowDate());
         }
         super.saveOrUpdate(liveWatchUser);
+        return liveWatchUser;
     }
     @Override
-    public void close(long liveId, long userId) {
+    public LiveWatchUser close(long liveId, long userId) {
         LiveWatchUser liveWatchUser = getByLiveIdAndUserId(liveId, userId);
         liveWatchUser.setUpdateTime(DateUtils.getNowDate());
         liveWatchUser.setOnline(1);
         super.updateById(liveWatchUser);
+        return liveWatchUser;
     }
 
     /**

+ 18 - 0
fs-service/src/main/java/com/fs/live/vo/LiveGoodsVo.java

@@ -0,0 +1,18 @@
+package com.fs.live.vo;
+
+
+import lombok.AllArgsConstructor;
+import lombok.Data;
+
+import java.math.BigDecimal;
+
+@Data
+@AllArgsConstructor
+public class LiveGoodsVo {
+    private Long goodsId;
+    private String imgUrl;
+    private String productName;
+    private BigDecimal price;
+    private Integer stock;
+    private Integer sales;
+}

+ 10 - 0
fs-service/src/main/resources/mapper/his/FsStoreProductMapper.xml

@@ -238,4 +238,14 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
             #{productId}
         </foreach>
     </delete>
+
+    <select id="selectFsStoreProductByProductIds" parameterType="list" resultMap="FsStoreProductResult">
+        <include refid="selectFsStoreProductVo"/>
+        <where>
+            product_id IN
+            <foreach collection="productIdList" item="id" open="(" separator="," close=")">
+                #{id}
+            </foreach>
+        </where>
+    </select>
 </mapper>

+ 39 - 0
fs-service/src/main/resources/mapper/live/LiveGoodsMapper.xml

@@ -112,4 +112,43 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
     <select id="selectStoreIdByLiveId" parameterType="Long">
         select distinct store_id from live_goods where live_id = #{liveId}
     </select>
+    <insert id="insertLiveGoodsList">
+        INSERT INTO live_goods (
+        live_id, company_id, company_user_id, store_id,
+        product_id, create_time, create_by, update_by,
+        update_time, remark, status, stock, sort
+        ) VALUES
+        <foreach collection="liveGoodsList" item="item" separator=",">
+            (
+            #{item.liveId}, #{item.companyId}, #{item.companyUserId}, #{item.storeId},
+            #{item.productId}, #{item.createTime}, #{item.createBy}, #{item.updateBy},
+            #{item.updateTime}, #{item.remark}, #{item.status}, #{item.stock}, #{item.sort}
+            )
+        </foreach>
+    </insert>
+
+    <select id="selectProductIdsByLiveId" resultType="string">
+        SELECT product_id
+        FROM live_goods
+        WHERE live_id = #{liveId}
+    </select>
+
+    <select id="selectProductListByLiveId" parameterType="LiveGoods" resultType="com.fs.live.vo.LiveGoodsVo">
+
+        select lg.goods_id,sp.img_url,sp.product_name,sp.price,sp.stock,sp.sales from live_goods lg
+        LEFT JOIN fs_store_product sp
+        ON lg.store_id = sp.store_id AND lg.product_id = sp.product_id
+
+        <where>
+            <if test="liveId != null "> and live_id = #{liveId}</if>
+            <if test="companyId != null "> and company_id = #{companyId}</if>
+            <if test="companyUserId != null "> and company_user_id = #{companyUserId}</if>
+            <if test="storeId != null "> and store_id = #{storeId}</if>
+            <if test="productId != null "> and product_id = #{productId}</if>
+            <if test="status != null "> and status = #{status}</if>
+            <if test="stock != null "> and stock = #{stock}</if>
+            <if test="sort != null "> and sort = #{sort}</if>
+        </where>
+    </select>
+
 </mapper>