Răsfoiți Sursa

价格表-酒吧相关通用代码,临时版本,防止冲突

liyafei 3 zile în urmă
părinte
comite
80cea8c2c3
21 a modificat fișierele cu 2139 adăugiri și 15 ștergeri
  1. 24 0
      alien-entity/src/main/java/shop/alien/entity/result/CommonEnum.java
  2. 102 0
      alien-entity/src/main/java/shop/alien/entity/store/StoreProductBar.java
  3. 91 0
      alien-entity/src/main/java/shop/alien/entity/store/StoreProductDelicacies.java
  4. 102 0
      alien-entity/src/main/java/shop/alien/entity/store/StoreProductGym.java
  5. 10 5
      alien-entity/src/main/java/shop/alien/entity/store/StoreProductItem.java
  6. 58 0
      alien-entity/src/main/java/shop/alien/entity/store/dto/StoreProductItemDto.java
  7. 48 0
      alien-entity/src/main/java/shop/alien/mapper/StoreProductItemMapper.java
  8. 76 0
      alien-entity/src/main/resources/mapper/StoreProductItemMapper.xml
  9. 0 2
      alien-store/src/main/java/shop/alien/store/config/MyBatisFieldHandler.java
  10. 185 0
      alien-store/src/main/java/shop/alien/store/controller/StoreProductBarController.java
  11. 204 0
      alien-store/src/main/java/shop/alien/store/controller/StoreProductDelicaciesController.java
  12. 170 0
      alien-store/src/main/java/shop/alien/store/controller/StoreProductGymController.java
  13. 43 8
      alien-store/src/main/java/shop/alien/store/controller/StoreProductItemController.java
  14. 99 0
      alien-store/src/main/java/shop/alien/store/service/StoreProductBarService.java
  15. 103 0
      alien-store/src/main/java/shop/alien/store/service/StoreProductDelicaciesService.java
  16. 87 0
      alien-store/src/main/java/shop/alien/store/service/StoreProductGymService.java
  17. 71 0
      alien-store/src/main/java/shop/alien/store/service/StoreProductItemService.java
  18. 183 0
      alien-store/src/main/java/shop/alien/store/service/impl/StoreProductBarServiceImpl.java
  19. 176 0
      alien-store/src/main/java/shop/alien/store/service/impl/StoreProductDelicaciesServiceImpl.java
  20. 164 0
      alien-store/src/main/java/shop/alien/store/service/impl/StoreProductGymServiceImpl.java
  21. 143 0
      alien-store/src/main/java/shop/alien/store/service/impl/StoreProductItemServiceImpl.java

+ 24 - 0
alien-entity/src/main/java/shop/alien/entity/result/CommonEnum.java

@@ -0,0 +1,24 @@
+package shop.alien.entity.result;
+
+
+public interface CommonEnum {
+
+      enum StoreProductItemProdType {
+        BAR_DRINK(1, "酒吧-酒水"),
+        BAR_FOOD(2, "酒吧-餐食"),
+        DELICACY_FOOD(3, "美食-餐食"),
+        GYM_SINGLE(4, "运动健身-单次"),
+        GYM_MULTI(5, "运动健身-多次");
+
+        private final int code;
+        private final String desc;
+
+        StoreProductItemProdType(int code, String desc) {
+            this.code = code;
+            this.desc = desc;
+        }
+
+        public int getCode() { return code; }
+        public String getDesc() { return desc; }
+    }
+}

+ 102 - 0
alien-entity/src/main/java/shop/alien/entity/store/StoreProductBar.java

@@ -0,0 +1,102 @@
+package shop.alien.entity.store;
+
+import com.baomidou.mybatisplus.annotation.*;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import com.fasterxml.jackson.annotation.JsonInclude;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.util.Date;
+
+/**
+ * 酒吧商品表
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+@Data
+@JsonInclude
+@TableName("store_product_bar")
+@ApiModel(value = "StoreProductBar对象", description = "酒吧商品表")
+public class StoreProductBar implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    @ApiModelProperty(value = "主键")
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "商品表主键")
+    @TableField("ext_id")
+    private Integer extId;
+
+    @ApiModelProperty(value = "区分套餐下的酒水1,餐食2")
+    @TableField("sub_type")
+    private int sub_type;
+
+    @ApiModelProperty(value = "名称(酒水,餐食)")
+    @TableField("name")
+    private String name;
+
+    @ApiModelProperty(value = "价格(¥)")
+    @TableField("price")
+    private BigDecimal price;
+
+    @ApiModelProperty(value = "成本价(¥)")
+    @TableField("cost_price")
+    private BigDecimal costPrice;
+
+    @ApiModelProperty(value = "单位,如份/瓶/杯")
+    @TableField("unit")
+    private String unit;
+
+    @ApiModelProperty(value = "数量")
+    @TableField("quantity")
+    private Integer quantity;
+
+    @ApiModelProperty(value = "品类")
+    @TableField("category")
+    private String category;
+
+    @ApiModelProperty(value = "酒精度(%vol)")
+    @TableField("alcohol_vol")
+    private BigDecimal alcoholVol;
+
+    @ApiModelProperty(value = "酒水体积(ml)")
+    @TableField("volume_ml")
+    private Integer volumeMl;
+
+    @ApiModelProperty(value = "风味")
+    @TableField("flavor")
+    private String flavor;
+
+    @ApiModelProperty(value = "状态:0禁用,1启用")
+    @TableField("status")
+    private Integer status;
+
+    @ApiModelProperty(value = "删除标记, 0:未删除, 1:已删除")
+    @TableField("delete_flag")
+    @TableLogic
+    private Integer deleteFlag;
+
+    @ApiModelProperty(value = "创建人")
+    @TableField("created_user_id")
+    private Integer createdUserId;
+
+    @ApiModelProperty(value = "更新人")
+    @TableField("updated_user_id")
+    private Integer updatedUserId;
+
+    @ApiModelProperty(value = "创建时间")
+    @TableField(value = "created_time", fill = FieldFill.INSERT)
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
+    private Date createdTime;
+
+    @ApiModelProperty(value = "更新时间")
+    @TableField(value = "updated_time", fill = FieldFill.UPDATE)
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
+    private Date updatedTime;
+}

+ 91 - 0
alien-entity/src/main/java/shop/alien/entity/store/StoreProductDelicacies.java

@@ -0,0 +1,91 @@
+package shop.alien.entity.store;
+
+import com.baomidou.mybatisplus.annotation.*;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import com.fasterxml.jackson.annotation.JsonInclude;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.util.Date;
+
+/**
+ * 美食商品表
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+@Data
+@JsonInclude
+@TableName("store_product_delicacies")
+@ApiModel(value = "StoreProductDelicacies对象", description = "美食商品表")
+public class StoreProductDelicacies implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    @ApiModelProperty(value = "主键")
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "商品表主键")
+    @TableField("ext_id")
+    private Integer extId;
+
+    @ApiModelProperty(value = "名称")
+    @TableField("name")
+    private String name;
+
+    @ApiModelProperty(value = "价格(¥)")
+    @TableField("price")
+    private BigDecimal price;
+
+    @ApiModelProperty(value = "成本价(¥)")
+    @TableField("cost_price")
+    private BigDecimal costPrice;
+
+    @ApiModelProperty(value = "单位,如份/瓶/杯")
+    @TableField("unit")
+    private String unit;
+
+    @ApiModelProperty(value = "数量")
+    @TableField("quantity")
+    private Integer quantity;
+
+    @ApiModelProperty(value = "类别")
+    @TableField("category")
+    private String category;
+
+    @ApiModelProperty(value = "菜品分组")
+    @TableField("ext_group")
+    private String extGroup;
+
+    @ApiModelProperty(value = "状态:0禁用,1启用")
+    @TableField("status")
+    private Integer status;
+
+    @ApiModelProperty(value = "删除标记, 0:未删除, 1:已删除")
+    @TableField("delete_flag")
+    @TableLogic
+    private Integer deleteFlag;
+
+    @ApiModelProperty(value = "创建人")
+    @TableField("created_user_id")
+    private Integer createdUserId;
+
+    @ApiModelProperty(value = "更新人")
+    @TableField("updated_user_id")
+    private Integer updatedUserId;
+
+    @ApiModelProperty(value = "创建时间")
+    @TableField(value = "created_time", fill = FieldFill.INSERT)
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
+    private Date createdTime;
+
+    @ApiModelProperty(value = "更新时间")
+    @TableField(value = "updated_time", fill = FieldFill.UPDATE)
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
+    private Date updatedTime;
+}
+

+ 102 - 0
alien-entity/src/main/java/shop/alien/entity/store/StoreProductGym.java

@@ -0,0 +1,102 @@
+package shop.alien.entity.store;
+
+import com.baomidou.mybatisplus.annotation.*;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import com.fasterxml.jackson.annotation.JsonInclude;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.util.Date;
+
+/**
+ * 运动健身商品表
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+@Data
+@JsonInclude
+@TableName("store_product_gym")
+@ApiModel(value = "StoreProductGym对象", description = "运动健身商品表")
+public class StoreProductGym implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    @ApiModelProperty(value = "主键")
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "商品表主键")
+    @TableField("ext_id")
+    private Integer extId;
+
+    @ApiModelProperty(value = "名称")
+    @TableField("name")
+    private String name;
+
+    @ApiModelProperty(value = "上课形式,如一对一/小班课")
+    @TableField("class_mode")
+    private String classMode;
+
+    @ApiModelProperty(value = "可用周期(天)")
+    @TableField("available_days")
+    private Integer availableDays;
+
+    @ApiModelProperty(value = "总课时数(节)")
+    @TableField("total_sessions")
+    private Integer totalSessions;
+
+    @ApiModelProperty(value = "价格(¥)")
+    @TableField("price")
+    private BigDecimal price;
+
+    @ApiModelProperty(value = "课程功效")
+    @TableField("course_effect")
+    private String courseEffect;
+
+    @ApiModelProperty(value = "适用人群")
+    @TableField("suitable_people")
+    private String suitablePeople;
+
+    @ApiModelProperty(value = "适用会员")
+    @TableField("suitable_membership")
+    private String suitableMembership;
+
+    @ApiModelProperty(value = "淋浴设施")
+    @TableField("shower_facility")
+    private String showerFacility;
+
+    @ApiModelProperty(value = "额外须知")
+    @TableField("extra_notice")
+    private String extraNotice;
+
+    @ApiModelProperty(value = "状态:0禁用,1启用")
+    @TableField("status")
+    private Integer status;
+
+    @ApiModelProperty(value = "删除标记, 0:未删除, 1:已删除")
+    @TableField("delete_flag")
+    @TableLogic
+    private Integer deleteFlag;
+
+    @ApiModelProperty(value = "创建人")
+    @TableField("created_user_id")
+    private Integer createdUserId;
+
+    @ApiModelProperty(value = "更新人")
+    @TableField("updated_user_id")
+    private Integer updatedUserId;
+
+    @ApiModelProperty(value = "创建时间")
+    @TableField(value = "created_time", fill = FieldFill.INSERT)
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
+    private Date createdTime;
+
+    @ApiModelProperty(value = "更新时间")
+    @TableField(value = "updated_time", fill = FieldFill.UPDATE)
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
+    private Date updatedTime;
+}

+ 10 - 5
alien-entity/src/main/java/shop/alien/entity/store/StoreProductItem.java

@@ -8,6 +8,7 @@ import io.swagger.annotations.ApiModelProperty;
 import lombok.Data;
 
 import java.io.Serializable;
+import java.math.BigDecimal;
 import java.util.Date;
 
 /**
@@ -26,11 +27,11 @@ public class StoreProductItem implements Serializable {
 
     @ApiModelProperty(value = "主键")
     @TableId(value = "id", type = IdType.AUTO)
-    private Long id;
+    private Integer id;
 
     @ApiModelProperty(value = "父id")
-    @TableField(value = "pid", fill = FieldFill.INSERT)
-    private Long pid;
+    @TableField(value = "pid")
+    private Integer pid;
 
     @ApiModelProperty(value = "门店id")
     @TableField("store_id")
@@ -40,6 +41,10 @@ public class StoreProductItem implements Serializable {
     @TableField("prod_name")
     private String prodName;
 
+    @ApiModelProperty(value = "总价")
+    @TableField("total_price")
+    private BigDecimal totalPrice;
+
     @ApiModelProperty(value = "商品类型,整型枚举:1酒吧-酒水 2酒吧-餐食 3美食-餐食 4运动健身-单次 5运动健身-多次")
     @TableField("prod_type")
     private Integer prodType;
@@ -91,11 +96,11 @@ public class StoreProductItem implements Serializable {
 
     @ApiModelProperty(value = "创建人")
     @TableField("created_user_id")
-    private Long createdUserId;
+    private Integer createdUserId;
 
     @ApiModelProperty(value = "更新人")
     @TableField("updated_user_id")
-    private Long updatedUserId;
+    private Integer updatedUserId;
 
     @ApiModelProperty(value = "创建时间")
     @TableField(value = "created_time", fill = FieldFill.INSERT)

+ 58 - 0
alien-entity/src/main/java/shop/alien/entity/store/dto/StoreProductItemDto.java

@@ -0,0 +1,58 @@
+package shop.alien.entity.store.dto;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.io.Serializable;
+import java.util.List;
+
+@Data
+@ApiModel(value = "StoreProductItemDto", description = "商品表 DTO")
+public class StoreProductItemDto implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    @ApiModelProperty("区分模块:1酒吧 2美食 3运动健身")
+    private Integer modelType;
+
+    @ApiModelProperty("主键")
+    private Integer id;
+
+    @ApiModelProperty("门店id")
+    private Integer storeId;
+
+    @ApiModelProperty("商品名称")
+    private String prodName;
+
+    @ApiModelProperty("商品类型,整型枚举:1酒吧-酒水 2酒吧-餐食 3美食-餐食 4运动健身-单次 5运动健身-多次")
+    private Integer prodType;
+
+    @ApiModelProperty("图片列表,最多 9 张 URL")
+    private String images;
+
+    @ApiModelProperty("图文详情-图片")
+    private String imageContent;
+
+    @ApiModelProperty("图文详情-文字")
+    private String detailContent;
+
+    @ApiModelProperty("补充说明")
+    private String extraNote;
+
+    @ApiModelProperty("是否需要预约:0=否,1=是")
+    private Integer needReserve;
+
+    @ApiModelProperty("预约规则")
+    private String reserveRule;
+
+    @ApiModelProperty("适用人数")
+    private Integer peopleLimit;
+
+    @ApiModelProperty("使用规则")
+    private String usageRule;
+
+    @ApiModelProperty("子项列表(后端按类型转换)")
+    private List<?> subList;
+
+}

+ 48 - 0
alien-entity/src/main/java/shop/alien/mapper/StoreProductItemMapper.java

@@ -0,0 +1,48 @@
+package shop.alien.mapper;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import org.apache.ibatis.annotations.Mapper;
+import org.apache.ibatis.annotations.Param;
+import shop.alien.entity.store.StoreProductItem;
+import shop.alien.entity.store.dto.StoreProductItemDto;
+
+import java.util.ArrayList;
+import shop.alien.entity.store.vo.StoreProductItemGymVo;
+
+/**
+ * <p>
+ * 商品表 Mapper 接口
+ * </p>
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+@Mapper
+public interface StoreProductItemMapper extends BaseMapper<StoreProductItem> {
+
+    ArrayList<StoreProductItemDto> getByPId(Integer id);
+    /**
+     * 分页查询商品表与运动健身商品表关联数据
+     *
+     * @param page 分页对象
+     * @param storeId 门店ID
+     * @param prodName 商品名称(模糊查询)
+     * @param prodType 商品类型
+     * @return IPage<StoreProductItemGymVo>
+     */
+    IPage<StoreProductItemGymVo> getPageWithGym(Page<StoreProductItemGymVo> page,
+                                                 @Param("storeId") Integer storeId,
+                                                 @Param("prodName") String prodName,
+                                                 @Param("prodType") Integer prodType);
+
+    /**
+     * 根据ID查询商品表与运动健身商品表关联详情
+     *
+     * @param id 商品表主键ID
+     * @return StoreProductItemGymVo
+     */
+    StoreProductItemGymVo getDetailWithGym(@Param("id") Long id);
+}
+

+ 76 - 0
alien-entity/src/main/resources/mapper/StoreProductItemMapper.xml

@@ -32,6 +32,82 @@
         extra_note, need_reserve, reserve_rule, people_limit, usage_rule, status, 
         rejection_reason, delete_flag, created_user_id, updated_user_id, created_time, updated_time
     </sql>
+    <!-- 酒吧商品模块 -->
+    <resultMap id="StoreProductItemDtoMap" type="shop.alien.entity.store.dto.StoreProductItemDto">
+        <id column="id" property="id"/>
+        <result column="store_id" property="storeId"/>
+        <result column="prod_name" property="prodName"/>
+        <result column="prod_type" property="prodType"/>
+        <result column="images" property="images"/>
+        <result column="image_content" property="imageContent"/>
+        <result column="detail_content" property="detailContent"/>
+        <result column="extra_note" property="extraNote"/>
+        <result column="need_reserve" property="needReserve"/>
+        <result column="reserve_rule" property="reserveRule"/>
+        <result column="people_limit" property="peopleLimit"/>
+        <result column="usage_rule" property="usageRule"/>
+
+        <collection property="subList" ofType="shop.alien.entity.store.StoreProductBar">
+            <id column="bar_id" property="id"/>
+            <result column="bar_ext_id" property="extId"/>
+            <result column="sub_type" property="sub_type"/>
+            <result column="name" property="name"/>
+            <result column="price" property="price"/>
+            <result column="cost_price" property="costPrice"/>
+            <result column="unit" property="unit"/>
+            <result column="quantity" property="quantity"/>
+            <result column="category" property="category"/>
+            <result column="alcohol_vol" property="alcoholVol"/>
+            <result column="volume_ml" property="volumeMl"/>
+            <result column="flavor" property="flavor"/>
+            <result column="bar_status" property="status"/>
+            <result column="bar_delete_flag" property="deleteFlag"/>
+            <result column="created_user_id" property="createdUserId" />
+            <result column="updated_user_id" property="updatedUserId" />
+            <result column="bar_created_time" property="createdTime"/>
+            <result column="bar_updated_time" property="updatedTime"/>
+        </collection>
+    </resultMap>
+
+    <select id="getByPId" resultMap="StoreProductItemDtoMap">
+        SELECT
+            spi.id,
+            spi.store_id,
+            spi.prod_name,
+            spi.prod_type,
+            spi.images,
+            spi.image_content,
+            spi.detail_content,
+            spi.extra_note,
+            spi.need_reserve,
+            spi.reserve_rule,
+            spi.people_limit,
+            spi.usage_rule,
+            spb.id           AS bar_id,
+            spb.ext_id       AS bar_ext_id,
+            spb.sub_type,
+            spb.name,
+            spb.price,
+            spb.cost_price,
+            spb.unit,
+            spb.quantity,
+            spb.category,
+            spb.alcohol_vol,
+            spb.volume_ml,
+            spb.flavor,
+            spb.status       AS bar_status,
+            spb.delete_flag  AS bar_delete_flag,
+            spb.created_user_id AS bar_created_user_id,
+            spb.updated_user_id AS bar_updated_user_id,
+            spb.created_time AS bar_created_time,
+            spb.updated_time AS bar_updated_time
+        FROM store_product_item spi
+                 LEFT JOIN store_product_bar spb
+                           ON spb.ext_id = spi.id
+                               AND spb.delete_flag = 0
+        WHERE spi.pid = #{id}
+          AND spi.delete_flag = 0
+    </select>
 
 </mapper>
 

+ 0 - 2
alien-store/src/main/java/shop/alien/store/config/MyBatisFieldHandler.java

@@ -36,8 +36,6 @@ public class MyBatisFieldHandler implements MetaObjectHandler {
         //字段为实体类名, 不是表字段名
         this.setFieldValByName("createdTime", new Date(), metaObject);
         this.setFieldValByName("updatedTime", new Date(), metaObject);
-        // 设置pid默认值为0
-        this.setFieldValByName("pid", 0L, metaObject);
         if (JwtUtil.hasToken()) {
             this.setFieldValByName("createdUserId", Objects.requireNonNull(JwtUtil.getCurrentUserInfo()).getInteger("userId"), metaObject);
             this.setFieldValByName("updatedUserId", Objects.requireNonNull(JwtUtil.getCurrentUserInfo()).getInteger("userId"), metaObject);

+ 185 - 0
alien-store/src/main/java/shop/alien/store/controller/StoreProductBarController.java

@@ -0,0 +1,185 @@
+package shop.alien.store.controller;
+
+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.store.StoreProductBar;
+import shop.alien.store.service.StoreProductBarService;
+
+import java.util.List;
+
+/**
+ * 酒吧商品表 Controller
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+@Slf4j
+@Api(tags = {"酒吧商品管理"})
+@CrossOrigin
+@RestController
+@RequestMapping("/store/product/bar")
+@RequiredArgsConstructor
+public class StoreProductBarController {
+
+    private final StoreProductBarService storeProductBarService;
+
+    @ApiOperation("新增酒吧商品")
+    @ApiOperationSupport(order = 1)
+    @PostMapping
+    public R<String> saveBar(@RequestBody StoreProductBar bar) {
+        log.info("StoreProductBarController.saveBar?bar={}", bar);
+        // 参数校验
+        if (bar.getName() == null || bar.getName().trim().isEmpty()) {
+            return R.fail("名称不能为空");
+        }
+        if (bar.getPrice() == null) {
+            return R.fail("价格不能为空");
+        }
+        if (bar.getCostPrice() == null) {
+            return R.fail("成本价不能为空");
+        }
+        if (bar.getCategory() == null || bar.getCategory().trim().isEmpty()) {
+            return R.fail("品类不能为空");
+        }
+
+        R<StoreProductBar> result = storeProductBarService.addStoreProductBar(bar);
+        if (result.getCode() == 200) {
+            return R.success("新增成功");
+        }
+        return R.fail(result.getMsg());
+    }
+
+    @ApiOperation("修改酒吧商品")
+    @ApiOperationSupport(order = 2)
+    @PutMapping
+    public R<String> updateBar(@RequestBody StoreProductBar bar) {
+        log.info("StoreProductBarController.updateBar?bar={}", bar);
+        if (bar.getId() == null) {
+            return R.fail("ID不能为空");
+        }
+
+        R<StoreProductBar> result = storeProductBarService.editStoreProductBar(bar);
+        if (result.getCode() == 200) {
+            return R.success("修改成功");
+        }
+        return R.fail(result.getMsg());
+    }
+
+    @ApiOperation("删除酒吧商品")
+    @ApiOperationSupport(order = 3)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "id", value = "主键ID", dataType = "Integer", paramType = "path", required = true)
+    })
+    @DeleteMapping("/{id}")
+    public R<String> deleteBar(@PathVariable("id") Integer id) {
+        log.info("StoreProductBarController.deleteBar?id={}", id);
+        R<Boolean> result = storeProductBarService.deleteStoreProductBar(id);
+        if (result.getCode() == 200) {
+            return R.success("删除成功");
+        }
+        return R.fail(result.getMsg());
+    }
+
+    @ApiOperation("根据ID查询酒吧商品详情")
+    @ApiOperationSupport(order = 4)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "id", value = "主键ID", dataType = "Integer", paramType = "path", required = true)
+    })
+    @GetMapping("/{id}")
+    public R<StoreProductBar> getById(@PathVariable("id") Integer id) {
+        log.info("StoreProductBarController.getById?id={}", id);
+        R<StoreProductBar> result = storeProductBarService.getStoreProductBarById(id);
+        if (result.getCode() == 200 && result.getData() != null) {
+            return result;
+        }
+        return R.fail("未找到该酒吧商品信息");
+    }
+
+    @ApiOperation("分页查询酒吧商品列表")
+    @ApiOperationSupport(order = 5)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "pageNum", value = "页码", dataType = "int", paramType = "query", required = true),
+            @ApiImplicitParam(name = "pageSize", value = "页容", dataType = "int", paramType = "query", required = true),
+            @ApiImplicitParam(name = "name", value = "名称(模糊查询)", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "category", value = "品类", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "status", value = "状态(0:禁用,1:启用)", dataType = "Integer", paramType = "query"),
+            @ApiImplicitParam(name = "extId", value = "商品表主键", dataType = "Integer", paramType = "query")
+    })
+    @GetMapping("/page")
+    public R<IPage<StoreProductBar>> getPage(
+            @RequestParam(defaultValue = "1") int pageNum,
+            @RequestParam(defaultValue = "10") int pageSize,
+            @RequestParam(required = false) String name,
+            @RequestParam(required = false) String category,
+            @RequestParam(required = false) Integer status,
+            @RequestParam(required = false) Integer extId) {
+        log.info("StoreProductBarController.getPage?pageNum={}, pageSize={}, name={}, category={}, status={}, extId={}",
+                pageNum, pageSize, name, category, status, extId);
+        IPage<StoreProductBar> page = storeProductBarService.getPage(pageNum, pageSize, name, category, status, extId);
+        return R.data(page);
+    }
+
+    @ApiOperation("批量删除酒吧商品")
+    @ApiOperationSupport(order = 6)
+    @PostMapping("/batchDelete")
+    public R<String> deleteBatch(@RequestBody List<Integer> ids) {
+        log.info("StoreProductBarController.deleteBatch?ids={}", ids);
+        if (ids == null || ids.isEmpty()) {
+            return R.fail("ID列表不能为空");
+        }
+        boolean result = storeProductBarService.deleteBatch(ids);
+        if (result) {
+            return R.success("批量删除成功");
+        }
+        return R.fail("批量删除失败");
+    }
+
+    @ApiOperation("更新酒吧商品状态")
+    @ApiOperationSupport(order = 7)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "id", value = "主键ID", dataType = "Integer", paramType = "path", required = true),
+            @ApiImplicitParam(name = "status", value = "状态(0:禁用,1:启用)", dataType = "Integer", paramType = "query", required = true)
+    })
+    @PutMapping("/{id}/status")
+    public R<String> updateStatus(
+            @PathVariable("id") Integer id,
+            @RequestParam("status") Integer status) {
+        log.info("StoreProductBarController.updateStatus?id={}, status={}", id, status);
+        if (status == null || (status != 0 && status != 1)) {
+            return R.fail("状态值无效,只能为0或1");
+        }
+        boolean result = storeProductBarService.updateStatus(id, status);
+        if (result) {
+            return R.success("状态更新成功");
+        }
+        return R.fail("状态更新失败");
+    }
+
+    @ApiOperation("根据商品表主键查询酒吧商品列表")
+    @ApiOperationSupport(order = 8)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "extId", value = "商品表主键", dataType = "Integer", paramType = "query", required = true)
+    })
+    @GetMapping("/listByExtId")
+    public R<List<StoreProductBar>> getListByExtId(@RequestParam("extId") Integer extId) {
+        log.info("StoreProductBarController.getListByExtId?extId={}", extId);
+        List<StoreProductBar> list = storeProductBarService.getListByExtId(extId);
+        return R.data(list);
+    }
+
+    @ApiOperation("根据品类查询酒吧商品列表")
+    @ApiOperationSupport(order = 9)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "category", value = "品类", dataType = "String", paramType = "query", required = true)
+    })
+    @GetMapping("/listByCategory")
+    public R<List<StoreProductBar>> getListByCategory(@RequestParam("category") String category) {
+        log.info("StoreProductBarController.getListByCategory?category={}", category);
+        List<StoreProductBar> list = storeProductBarService.getListByCategory(category);
+        return R.data(list);
+    }
+}

+ 204 - 0
alien-store/src/main/java/shop/alien/store/controller/StoreProductDelicaciesController.java

@@ -0,0 +1,204 @@
+package shop.alien.store.controller;
+
+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.store.StoreProductDelicacies;
+import shop.alien.store.service.StoreProductDelicaciesService;
+
+import java.util.List;
+
+/**
+ * 美食商品表 Controller
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+@Slf4j
+@Api(tags = {"美食商品管理"})
+@ApiSort(1)
+@CrossOrigin
+@RestController
+@RequestMapping("/store/product/delicacies")
+@RequiredArgsConstructor
+public class StoreProductDelicaciesController {
+
+    private final StoreProductDelicaciesService storeProductDelicaciesService;
+
+    @ApiOperation("分页查询美食商品列表")
+    @ApiOperationSupport(order = 1)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "pageNum", value = "页码", dataType = "int", paramType = "query", required = true),
+            @ApiImplicitParam(name = "pageSize", value = "页容", dataType = "int", paramType = "query", required = true),
+            @ApiImplicitParam(name = "name", value = "名称(模糊查询)", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "category", value = "类别", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "extGroup", value = "菜品分组", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "status", value = "状态(0:禁用,1:启用)", dataType = "Integer", paramType = "query"),
+            @ApiImplicitParam(name = "extId", value = "商品表主键", dataType = "Integer", paramType = "query")
+    })
+    @GetMapping("/page")
+    public R<IPage<StoreProductDelicacies>> getPage(
+            @RequestParam(defaultValue = "1") int pageNum,
+            @RequestParam(defaultValue = "10") int pageSize,
+            @RequestParam(required = false) String name,
+            @RequestParam(required = false) String category,
+            @RequestParam(required = false) String extGroup,
+            @RequestParam(required = false) Integer status,
+            @RequestParam(required = false) Integer extId) {
+        log.info("StoreProductDelicaciesController.getPage?pageNum={}, pageSize={}, name={}, category={}, extGroup={}, status={}, extId={}",
+                pageNum, pageSize, name, category, extGroup, status, extId);
+        IPage<StoreProductDelicacies> page = storeProductDelicaciesService.getPage(pageNum, pageSize, name, category, extGroup, status, extId);
+        return R.data(page);
+    }
+
+    @ApiOperation("根据ID查询美食商品详情")
+    @ApiOperationSupport(order = 2)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "id", value = "主键ID", dataType = "Integer", paramType = "path", required = true)
+    })
+    @GetMapping("/{id}")
+    public R<StoreProductDelicacies> getById(@PathVariable("id") Integer id) {
+        log.info("StoreProductDelicaciesController.getById?id={}", id);
+        StoreProductDelicacies delicacies = storeProductDelicaciesService.getById(id);
+        if (delicacies == null) {
+            return R.fail("未找到该美食商品信息");
+        }
+        return R.data(delicacies);
+    }
+
+    @ApiOperation("新增美食商品")
+    @ApiOperationSupport(order = 3)
+    @PostMapping
+    public R<String> saveDelicacies(@RequestBody StoreProductDelicacies delicacies) {
+        log.info("StoreProductDelicaciesController.saveDelicacies?delicacies={}", delicacies);
+        // 参数校验
+        if (delicacies.getName() == null || delicacies.getName().trim().isEmpty()) {
+            return R.fail("名称不能为空");
+        }
+        if (delicacies.getPrice() == null) {
+            return R.fail("价格不能为空");
+        }
+        if (delicacies.getCostPrice() == null) {
+            return R.fail("成本价不能为空");
+        }
+        if (delicacies.getCategory() == null || delicacies.getCategory().trim().isEmpty()) {
+            return R.fail("类别不能为空");
+        }
+        if (delicacies.getExtGroup() == null || delicacies.getExtGroup().trim().isEmpty()) {
+            return R.fail("菜品分组不能为空");
+        }
+
+        boolean result = storeProductDelicaciesService.saveDelicacies(delicacies);
+        if (result) {
+            return R.success("新增成功");
+        }
+        return R.fail("新增失败");
+    }
+
+    @ApiOperation("修改美食商品")
+    @ApiOperationSupport(order = 4)
+    @PutMapping
+    public R<String> updateDelicacies(@RequestBody StoreProductDelicacies delicacies) {
+        log.info("StoreProductDelicaciesController.updateDelicacies?delicacies={}", delicacies);
+        if (delicacies.getId() == null) {
+            return R.fail("ID不能为空");
+        }
+
+        boolean result = storeProductDelicaciesService.updateDelicacies(delicacies);
+        if (result) {
+            return R.success("修改成功");
+        }
+        return R.fail("修改失败");
+    }
+
+    @ApiOperation("删除美食商品")
+    @ApiOperationSupport(order = 5)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "id", value = "主键ID", dataType = "Long", paramType = "path", required = true)
+    })
+    @DeleteMapping("/{id}")
+    public R<String> deleteDelicacies(@PathVariable("id") Integer id) {
+        log.info("StoreProductDelicaciesController.deleteDelicacies?id={}", id);
+        boolean result = storeProductDelicaciesService.deleteDelicacies(id);
+        if (result) {
+            return R.success("删除成功");
+        }
+        return R.fail("删除失败");
+    }
+
+    @ApiOperation("批量删除美食商品")
+    @ApiOperationSupport(order = 6)
+    @PostMapping("/batchDelete")
+    public R<String> deleteBatch(@RequestBody List<Integer> ids) {
+        log.info("StoreProductDelicaciesController.deleteBatch?ids={}", ids);
+        if (ids == null || ids.isEmpty()) {
+            return R.fail("ID列表不能为空");
+        }
+        boolean result = storeProductDelicaciesService.deleteBatch(ids);
+        if (result) {
+            return R.success("批量删除成功");
+        }
+        return R.fail("批量删除失败");
+    }
+
+    @ApiOperation("更新美食商品状态")
+    @ApiOperationSupport(order = 7)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "id", value = "主键ID", dataType = "Integer", paramType = "path", required = true),
+            @ApiImplicitParam(name = "status", value = "状态(0:禁用,1:启用)", dataType = "Integer", paramType = "query", required = true)
+    })
+    @PutMapping("/{id}/status")
+    public R<String> updateStatus(
+            @PathVariable("id") Integer id,
+            @RequestParam("status") Integer status) {
+        log.info("StoreProductDelicaciesController.updateStatus?id={}, status={}", id, status);
+        if (status == null || (status != 0 && status != 1)) {
+            return R.fail("状态值无效,只能为0或1");
+        }
+        boolean result = storeProductDelicaciesService.updateStatus(id, status);
+        if (result) {
+            return R.success("状态更新成功");
+        }
+        return R.fail("状态更新失败");
+    }
+
+    @ApiOperation("根据商品表主键查询美食商品列表")
+    @ApiOperationSupport(order = 8)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "extId", value = "商品表主键", dataType = "Integer", paramType = "query", required = true)
+    })
+    @GetMapping("/listByExtId")
+    public R<List<StoreProductDelicacies>> getListByExtId(@RequestParam("extId") Integer extId) {
+        log.info("StoreProductDelicaciesController.getListByExtId?extId={}", extId);
+        List<StoreProductDelicacies> list = storeProductDelicaciesService.getListByExtId(extId);
+        return R.data(list);
+    }
+
+    @ApiOperation("根据类别查询美食商品列表")
+    @ApiOperationSupport(order = 9)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "category", value = "类别", dataType = "String", paramType = "query", required = true)
+    })
+    @GetMapping("/listByCategory")
+    public R<List<StoreProductDelicacies>> getListByCategory(@RequestParam("category") String category) {
+        log.info("StoreProductDelicaciesController.getListByCategory?category={}", category);
+        List<StoreProductDelicacies> list = storeProductDelicaciesService.getListByCategory(category);
+        return R.data(list);
+    }
+
+    @ApiOperation("根据菜品分组查询美食商品列表")
+    @ApiOperationSupport(order = 10)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "extGroup", value = "菜品分组", dataType = "String", paramType = "query", required = true)
+    })
+    @GetMapping("/listByExtGroup")
+    public R<List<StoreProductDelicacies>> getListByExtGroup(@RequestParam("extGroup") String extGroup) {
+        log.info("StoreProductDelicaciesController.getListByExtGroup?extGroup={}", extGroup);
+        List<StoreProductDelicacies> list = storeProductDelicaciesService.getListByExtGroup(extGroup);
+        return R.data(list);
+    }
+}
+

+ 170 - 0
alien-store/src/main/java/shop/alien/store/controller/StoreProductGymController.java

@@ -0,0 +1,170 @@
+package shop.alien.store.controller;
+
+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.store.StoreProductGym;
+import shop.alien.store.service.StoreProductGymService;
+
+import java.util.List;
+
+/**
+ * 运动健身商品表 Controller
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+@Slf4j
+@Api(tags = {"运动健身商品管理"})
+@CrossOrigin
+@RestController
+@RequestMapping("/store/product/gym")
+@RequiredArgsConstructor
+public class StoreProductGymController {
+
+    private final StoreProductGymService storeProductGymService;
+
+    @ApiOperation("新增运动健身商品")
+    @ApiOperationSupport(order = 1)
+    @PostMapping
+    public R<String> saveGym(@RequestBody StoreProductGym gym) {
+        log.info("StoreProductGymController.saveGym?gym={}", gym);
+        // 参数校验
+        if (gym.getName() == null || gym.getName().trim().isEmpty()) {
+            return R.fail("名称不能为空");
+        }
+        if (gym.getClassMode() == null || gym.getClassMode().trim().isEmpty()) {
+            return R.fail("上课形式不能为空");
+        }
+        if (gym.getPrice() == null) {
+            return R.fail("价格不能为空");
+        }
+
+        R<StoreProductGym> result = storeProductGymService.addStoreProductGym(gym);
+        if (result.getCode() == 200) {
+            return R.success("新增成功");
+        }
+        return R.fail(result.getMsg());
+    }
+
+    @ApiOperation("修改运动健身商品")
+    @ApiOperationSupport(order = 2)
+    @PutMapping
+    public R<String> updateGym(@RequestBody StoreProductGym gym) {
+        log.info("StoreProductGymController.updateGym?gym={}", gym);
+        if (gym.getId() == null) {
+            return R.fail("ID不能为空");
+        }
+
+        R<StoreProductGym> result = storeProductGymService.editStoreProductGym(gym);
+        if (result.getCode() == 200) {
+            return R.success("修改成功");
+        }
+        return R.fail(result.getMsg());
+    }
+
+    @ApiOperation("删除运动健身商品")
+    @ApiOperationSupport(order = 3)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "id", value = "主键ID", dataType = "Integer", paramType = "path", required = true)
+    })
+    @DeleteMapping("/{id}")
+    public R<String> deleteGym(@PathVariable("id") Integer id) {
+        log.info("StoreProductGymController.deleteGym?id={}", id);
+        R<Boolean> result = storeProductGymService.deleteStoreProductGym(id);
+        if (result.getCode() == 200) {
+            return R.success("删除成功");
+        }
+        return R.fail(result.getMsg());
+    }
+
+    @ApiOperation("根据ID查询运动健身商品详情")
+    @ApiOperationSupport(order = 4)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "id", value = "主键ID", dataType = "Integer", paramType = "path", required = true)
+    })
+    @GetMapping("/{id}")
+    public R<StoreProductGym> getById(@PathVariable("id") Integer id) {
+        log.info("StoreProductGymController.getById?id={}", id);
+        R<StoreProductGym> result = storeProductGymService.getStoreProductGymById(id);
+        if (result.getCode() == 200 && result.getData() != null) {
+            return result;
+        }
+        return R.fail("未找到该运动健身商品信息");
+    }
+
+    @ApiOperation("分页查询运动健身商品列表")
+    @ApiOperationSupport(order = 5)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "pageNum", value = "页码", dataType = "int", paramType = "query", required = true),
+            @ApiImplicitParam(name = "pageSize", value = "页容", dataType = "int", paramType = "query", required = true),
+            @ApiImplicitParam(name = "name", value = "名称(模糊查询)", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "classMode", value = "上课形式", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "status", value = "状态(0:禁用,1:启用)", dataType = "Integer", paramType = "query"),
+            @ApiImplicitParam(name = "extId", value = "商品表主键", dataType = "Integer", paramType = "query")
+    })
+    @GetMapping("/page")
+    public R<IPage<StoreProductGym>> getPage(
+            @RequestParam(defaultValue = "1") int pageNum,
+            @RequestParam(defaultValue = "10") int pageSize,
+            @RequestParam(required = false) String name,
+            @RequestParam(required = false) String classMode,
+            @RequestParam(required = false) Integer status,
+            @RequestParam(required = false) Integer extId) {
+        log.info("StoreProductGymController.getPage?pageNum={}, pageSize={}, name={}, classMode={}, status={}, extId={}",
+                pageNum, pageSize, name, classMode, status, extId);
+        IPage<StoreProductGym> page = storeProductGymService.getPage(pageNum, pageSize, name, classMode, status, extId);
+        return R.data(page);
+    }
+
+    @ApiOperation("批量删除运动健身商品")
+    @ApiOperationSupport(order = 6)
+    @PostMapping("/batchDelete")
+    public R<String> deleteBatch(@RequestBody List<Integer> ids) {
+        log.info("StoreProductGymController.deleteBatch?ids={}", ids);
+        if (ids == null || ids.isEmpty()) {
+            return R.fail("ID列表不能为空");
+        }
+        boolean result = storeProductGymService.deleteBatch(ids);
+        if (result) {
+            return R.success("批量删除成功");
+        }
+        return R.fail("批量删除失败");
+    }
+
+    @ApiOperation("更新运动健身商品状态")
+    @ApiOperationSupport(order = 7)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "id", value = "主键ID", dataType = "Integer", paramType = "path", required = true),
+            @ApiImplicitParam(name = "status", value = "状态(0:禁用,1:启用)", dataType = "Integer", paramType = "query", required = true)
+    })
+    @PutMapping("/{id}/status")
+    public R<String> updateStatus(
+            @PathVariable("id") Integer id,
+            @RequestParam("status") Integer status) {
+        log.info("StoreProductGymController.updateStatus?id={}, status={}", id, status);
+        if (status == null || (status != 0 && status != 1)) {
+            return R.fail("状态值无效,只能为0或1");
+        }
+        boolean result = storeProductGymService.updateStatus(id, status);
+        if (result) {
+            return R.success("状态更新成功");
+        }
+        return R.fail("状态更新失败");
+    }
+
+    @ApiOperation("根据商品表主键查询运动健身商品列表")
+    @ApiOperationSupport(order = 8)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "extId", value = "商品表主键", dataType = "Integer", paramType = "query", required = true)
+    })
+    @GetMapping("/listByExtId")
+    public R<List<StoreProductGym>> getListByExtId(@RequestParam("extId") Integer extId) {
+        log.info("StoreProductGymController.getListByExtId?extId={}", extId);
+        List<StoreProductGym> list = storeProductGymService.getListByExtId(extId);
+        return R.data(list);
+    }
+}

+ 43 - 8
alien-store/src/main/java/shop/alien/store/controller/StoreProductItemController.java

@@ -7,6 +7,8 @@ import lombok.extern.slf4j.Slf4j;
 import org.springframework.web.bind.annotation.*;
 import shop.alien.entity.result.R;
 import shop.alien.entity.store.StoreProductItem;
+import shop.alien.entity.store.dto.StoreProductItemDto;
+import shop.alien.entity.store.vo.StoreProductItemGymVo;
 import shop.alien.store.service.StoreProductItemService;
 import shop.alien.util.myBaticsPlus.QueryBuilder;
 
@@ -31,23 +33,23 @@ public class StoreProductItemController {
     @ApiOperation("新增商品")
     @ApiOperationSupport(order = 1)
     @PostMapping("/add")
-    public R<StoreProductItem> addStoreProductItem(@RequestBody StoreProductItem storeProductItem) {
-        log.info("StoreProductItemController.addStoreProductItem?storeProductItem={}", storeProductItem);
-        return storeProductItemService.addStoreProductItem(storeProductItem);
+    public R<StoreProductItem> addStoreProductItem(@RequestBody StoreProductItemDto storeProductItemDto) {
+        log.info("StoreProductItemController.addStoreProductItem?storeProductItem={}", storeProductItemDto);
+        return storeProductItemService.addStoreProductItemDto(storeProductItemDto);
     }
 
     @ApiOperation("编辑商品")
     @ApiOperationSupport(order = 2)
     @PostMapping("/edit")
-    public R<StoreProductItem> editStoreProductItem(@RequestBody StoreProductItem storeProductItem) {
-        log.info("StoreProductItemController.editStoreProductItem?storeProductItem={}", storeProductItem);
-        return storeProductItemService.editStoreProductItem(storeProductItem);
+    public R<StoreProductItem> editStoreProductItem(@RequestBody StoreProductItemDto storeProductItemDto) {
+        log.info("StoreProductItemController.editStoreProductItem?storeProductItem={}", storeProductItemDto);
+        return storeProductItemService.editStoreProductItem(storeProductItemDto);
     }
 
     @ApiOperation("删除商品")
     @ApiOperationSupport(order = 3)
     @DeleteMapping("/delete")
-    public R<Boolean> deleteStoreProductItem(@RequestParam(value = "id") Long id) {
+    public R<Boolean> deleteStoreProductItem(@RequestParam(value = "id") Integer id) {
         log.info("StoreProductItemController.deleteStoreProductItem?id={}", id);
         return storeProductItemService.deleteStoreProductItem(id);
     }
@@ -55,7 +57,7 @@ public class StoreProductItemController {
     @ApiOperation("根据ID查询商品")
     @ApiOperationSupport(order = 4)
     @GetMapping("/getById")
-    public R<StoreProductItem> getStoreProductItemById(@RequestParam(value = "id") Long id) {
+    public R<List<StoreProductItemDto>> getStoreProductItemById(@RequestParam(value = "id") Integer id) {
         log.info("StoreProductItemController.getStoreProductItemById?id={}", id);
         return storeProductItemService.getStoreProductItemById(id);
     }
@@ -124,5 +126,38 @@ public class StoreProductItemController {
                 .page(storeProductItemService);
         return R.data(pageResult);
     }
+
+    @ApiOperation("用户端 运动健身列表查询")
+    @ApiOperationSupport(order = 8)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "pageNum", value = "页码(默认1)", dataType = "int", paramType = "query"),
+            @ApiImplicitParam(name = "pageSize", value = "页容(默认10)", dataType = "int", paramType = "query"),
+            @ApiImplicitParam(name = "storeId", value = "门店ID", dataType = "Integer", paramType = "query"),
+            @ApiImplicitParam(name = "prodName", value = "商品名称(模糊查询)", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "prodType", value = "商品类型(1酒吧-酒水 2酒吧-餐食 3美食-餐食 4运动健身-单次 5运动健身-多次)", dataType = "Integer", paramType = "query")
+    })
+    @GetMapping("/getPageWithGym")
+    public R<IPage<StoreProductItemGymVo>> getPageWithGym(
+            @RequestParam int pageNum,
+            @RequestParam int pageSize,
+            @RequestParam(required = false) Integer storeId,
+            @RequestParam(required = false) String prodName,
+            @RequestParam(required = false) Integer prodType) {
+        log.info("StoreProductItemController.getPageWithGym?pageNum={}, pageSize={}, storeId={}, prodName={}, prodType={}",
+                pageNum, pageSize, storeId, prodName, prodType);
+        IPage<StoreProductItemGymVo> pageResult = storeProductItemService.getPageWithGym(pageNum, pageSize, storeId, prodName, prodType);
+        return R.data(pageResult);
+    }
+
+    @ApiOperation("用户端 运动健身详情查询")
+    @ApiOperationSupport(order = 9)
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "id", value = "商品表主键ID", dataType = "Long", paramType = "query", required = true)
+    })
+    @GetMapping("/getDetailWithGym")
+    public R<StoreProductItemGymVo> getDetailWithGym(@RequestParam("id") Long id) {
+        log.info("StoreProductItemController.getDetailWithGym?id={}", id);
+        return storeProductItemService.getDetailWithGym(id);
+    }
 }
 

+ 99 - 0
alien-store/src/main/java/shop/alien/store/service/StoreProductBarService.java

@@ -0,0 +1,99 @@
+package shop.alien.store.service;
+
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.service.IService;
+import shop.alien.entity.result.R;
+import shop.alien.entity.store.StoreProductBar;
+
+import java.util.List;
+
+/**
+ * 酒吧商品表 服务类
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+public interface StoreProductBarService extends IService<StoreProductBar> {
+
+    /**
+     * 新增酒吧商品
+     *
+     * @param storeProductBar 酒吧商品
+     * @return R<StoreProductBar>
+     */
+    R<StoreProductBar> addStoreProductBar(StoreProductBar storeProductBar);
+
+    /**
+     * 编辑酒吧商品
+     *
+     * @param storeProductBar 酒吧商品
+     * @return R<StoreProductBar>
+     */
+    R<StoreProductBar> editStoreProductBar(StoreProductBar storeProductBar);
+
+    /**
+     * 删除酒吧商品
+     *
+     * @param id 主键
+     * @return R<Boolean>
+     */
+    R<Boolean> deleteStoreProductBar(Integer id);
+
+    /**
+     * 根据ID查询酒吧商品
+     *
+     * @param id 主键
+     * @return R<StoreProductBar>
+     */
+    R<StoreProductBar> getStoreProductBarById(Integer id);
+
+    /**
+     * 分页查询酒吧商品列表
+     *
+     * @param pageNum  页码
+     * @param pageSize 页容
+     * @param name     名称(模糊查询)
+     * @param category 品类
+     * @param status   状态(0:禁用,1:启用)
+     * @param extId    商品表主键
+     * @return IPage<StoreProductBar>
+     */
+    IPage<StoreProductBar> getPage(int pageNum, int pageSize, String name, String category, Integer status, Integer extId);
+
+    /**
+     * 根据商品表主键查询酒吧商品列表
+     *
+     * @param extId 商品表主键
+     * @return List<StoreProductBar>
+     */
+    List<StoreProductBar> getListByExtId(Integer extId);
+
+    /**
+     * 根据品类查询酒吧商品列表
+     *
+     * @param category 品类
+     * @return List<StoreProductBar>
+     */
+    List<StoreProductBar> getListByCategory(String category);
+
+    /**
+     * 更新酒吧商品状态
+     *
+     * @param id     主键ID
+     * @param status 状态(0:禁用,1:启用)
+     * @return boolean
+     */
+    boolean updateStatus(Integer id, Integer status);
+
+    /**
+     * 批量删除酒吧商品(逻辑删除)
+     *
+     * @param ids 主键ID列表
+     * @return boolean
+     */
+    boolean deleteBatch(List<Integer> ids);
+
+
+    List<StoreProductBar> getByExtId(Integer id);
+
+}

+ 103 - 0
alien-store/src/main/java/shop/alien/store/service/StoreProductDelicaciesService.java

@@ -0,0 +1,103 @@
+package shop.alien.store.service;
+
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import shop.alien.entity.store.StoreProductDelicacies;
+
+import java.util.List;
+
+/**
+ * 美食商品表 服务类
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+public interface StoreProductDelicaciesService {
+
+    /**
+     * 分页查询美食商品列表
+     *
+     * @param pageNum  页码
+     * @param pageSize 页容
+     * @param name     名称(模糊查询)
+     * @param category 类别
+     * @param extGroup 菜品分组
+     * @param status   状态(0:禁用,1:启用)
+     * @param extId    商品表主键
+     * @return IPage<StoreProductDelicacies>
+     */
+    IPage<StoreProductDelicacies> getPage(int pageNum, int pageSize, String name, String category, String extGroup, Integer status, Integer extId);
+
+    /**
+     * 根据ID查询美食商品详情
+     *
+     * @param id 主键ID
+     * @return StoreProductDelicacies
+     */
+    StoreProductDelicacies getById(Integer id);
+
+    /**
+     * 新增美食商品
+     *
+     * @param delicacies 美食商品信息
+     * @return boolean
+     */
+    boolean saveDelicacies(StoreProductDelicacies delicacies);
+
+    /**
+     * 修改美食商品
+     *
+     * @param delicacies 美食商品信息
+     * @return boolean
+     */
+    boolean updateDelicacies(StoreProductDelicacies delicacies);
+
+    /**
+     * 删除美食商品(逻辑删除)
+     *
+     * @param id 主键ID
+     * @return boolean
+     */
+    boolean deleteDelicacies(Integer id);
+
+    /**
+     * 批量删除美食商品(逻辑删除)
+     *
+     * @param ids 主键ID列表
+     * @return boolean
+     */
+    boolean deleteBatch(List<Integer> ids);
+
+    /**
+     * 更新美食商品状态
+     *
+     * @param id     主键ID
+     * @param status 状态(0:禁用,1:启用)
+     * @return boolean
+     */
+    boolean updateStatus(Integer id, Integer status);
+
+    /**
+     * 根据商品表主键查询美食商品列表
+     *
+     * @param extId 商品表主键
+     * @return List<StoreProductDelicacies>
+     */
+    List<StoreProductDelicacies> getListByExtId(Integer extId);
+
+    /**
+     * 根据类别查询美食商品列表
+     *
+     * @param category 类别
+     * @return List<StoreProductDelicacies>
+     */
+    List<StoreProductDelicacies> getListByCategory(String category);
+
+    /**
+     * 根据菜品分组查询美食商品列表
+     *
+     * @param extGroup 菜品分组
+     * @return List<StoreProductDelicacies>
+     */
+    List<StoreProductDelicacies> getListByExtGroup(String extGroup);
+}
+

+ 87 - 0
alien-store/src/main/java/shop/alien/store/service/StoreProductGymService.java

@@ -0,0 +1,87 @@
+package shop.alien.store.service;
+
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.service.IService;
+import shop.alien.entity.result.R;
+import shop.alien.entity.store.StoreProductGym;
+
+import java.util.List;
+
+/**
+ * 运动健身商品表 服务类
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+public interface StoreProductGymService extends IService<StoreProductGym> {
+
+    /**
+     * 新增运动健身商品
+     *
+     * @param storeProductGym 运动健身商品
+     * @return R<StoreProductGym>
+     */
+    R<StoreProductGym> addStoreProductGym(StoreProductGym storeProductGym);
+
+    /**
+     * 编辑运动健身商品
+     *
+     * @param storeProductGym 运动健身商品
+     * @return R<StoreProductGym>
+     */
+    R<StoreProductGym> editStoreProductGym(StoreProductGym storeProductGym);
+
+    /**
+     * 删除运动健身商品
+     *
+     * @param id 主键
+     * @return R<Boolean>
+     */
+    R<Boolean> deleteStoreProductGym(Integer id);
+
+    /**
+     * 根据ID查询运动健身商品
+     *
+     * @param id 主键
+     * @return R<StoreProductGym>
+     */
+    R<StoreProductGym> getStoreProductGymById(Integer id);
+
+    /**
+     * 分页查询运动健身商品列表
+     *
+     * @param pageNum  页码
+     * @param pageSize 页容
+     * @param name     名称(模糊查询)
+     * @param classMode 上课形式
+     * @param status   状态(0:禁用,1:启用)
+     * @param extId    商品表主键
+     * @return IPage<StoreProductGym>
+     */
+    IPage<StoreProductGym> getPage(int pageNum, int pageSize, String name, String classMode, Integer status, Integer extId);
+
+    /**
+     * 根据商品表主键查询运动健身商品列表
+     *
+     * @param extId 商品表主键
+     * @return List<StoreProductGym>
+     */
+    List<StoreProductGym> getListByExtId(Integer extId);
+
+    /**
+     * 更新运动健身商品状态
+     *
+     * @param id     主键ID
+     * @param status 状态(0:禁用,1:启用)
+     * @return boolean
+     */
+    boolean updateStatus(Integer id, Integer status);
+
+    /**
+     * 批量删除运动健身商品(逻辑删除)
+     *
+     * @param ids 主键ID列表
+     * @return boolean
+     */
+    boolean deleteBatch(List<Integer> ids);
+}

+ 71 - 0
alien-store/src/main/java/shop/alien/store/service/StoreProductItemService.java

@@ -0,0 +1,71 @@
+package shop.alien.store.service;
+
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.service.IService;
+import shop.alien.entity.result.R;
+import shop.alien.entity.store.StoreProductItem;
+import shop.alien.entity.store.dto.StoreProductItemDto;
+import shop.alien.entity.store.vo.StoreProductItemGymVo;
+
+import java.util.List;
+
+/**
+ * 商品表 服务类
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+public interface StoreProductItemService extends IService<StoreProductItem> {
+
+    /**
+     * 新增商品
+     * @return R<StoreProductItem>
+     */
+    R<StoreProductItem> addStoreProductItemDto(StoreProductItemDto storeProductItemDto);
+
+    /**
+     * 编辑商品
+     *
+     * @param storeProductItem 商品
+     * @return R<StoreProductItem>
+     */
+    R<StoreProductItem> editStoreProductItem(StoreProductItemDto storeProductItem);
+
+    /**
+     * 删除商品
+     *
+     * @param id 主键
+     * @return R<Boolean>
+     */
+    R<Boolean> deleteStoreProductItem(Integer id);
+
+    /**
+     * 根据ID查询商品
+     *
+     * @param id 主键
+     * @return R<StoreProductItem>
+     */
+    R<List<StoreProductItemDto>> getStoreProductItemById(Integer id);
+
+
+    /**
+     * 分页查询商品表与运动健身商品表关联数据
+     *
+     * @param pageNum  页码
+     * @param pageSize 页容
+     * @param storeId  门店ID
+     * @param prodName 商品名称(模糊查询)
+     * @param prodType 商品类型
+     * @return IPage<StoreProductItemGymVo>
+     */
+    IPage<StoreProductItemGymVo> getPageWithGym(int pageNum, int pageSize, Integer storeId, String prodName, Integer prodType);
+
+    /**
+     * 根据ID查询商品表与运动健身商品表关联详情
+     *
+     * @param id 商品表主键ID
+     * @return R<StoreProductItemGymVo>
+     */
+    R<StoreProductItemGymVo> getDetailWithGym(Long id);
+}
+

+ 183 - 0
alien-store/src/main/java/shop/alien/store/service/impl/StoreProductBarServiceImpl.java

@@ -0,0 +1,183 @@
+package shop.alien.store.service.impl;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
+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.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+import org.springframework.util.StringUtils;
+import shop.alien.entity.result.R;
+import shop.alien.entity.store.StoreProductBar;
+import shop.alien.mapper.StoreProductBarMapper;
+import shop.alien.store.service.StoreProductBarService;
+
+import java.util.List;
+
+/**
+ * 酒吧商品表 服务实现类
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+@Slf4j
+@Transactional
+@Service
+@RequiredArgsConstructor
+public class StoreProductBarServiceImpl extends ServiceImpl<StoreProductBarMapper, StoreProductBar> implements StoreProductBarService {
+
+    @Override
+    public R<StoreProductBar> addStoreProductBar(StoreProductBar storeProductBar) {
+        log.info("StoreProductBarServiceImpl.addStoreProductBar?storeProductBar={}", storeProductBar);
+        // 设置默认值
+        if (storeProductBar.getUnit() == null || storeProductBar.getUnit().isEmpty()) {
+            storeProductBar.setUnit("份");
+        }
+        if (storeProductBar.getQuantity() == null) {
+            storeProductBar.setQuantity(0);
+        }
+        if (storeProductBar.getStatus() == null) {
+            storeProductBar.setStatus(1);
+        }
+        if (storeProductBar.getCreatedUserId() == null) {
+            storeProductBar.setCreatedUserId(0);
+        }
+        if (storeProductBar.getUpdatedUserId() == null) {
+            storeProductBar.setUpdatedUserId(0);
+        }
+
+        boolean result = this.save(storeProductBar);
+        if (result) {
+            return R.data(storeProductBar);
+        }
+        return R.fail("新增失败");
+    }
+
+    @Override
+    public R<StoreProductBar> editStoreProductBar(StoreProductBar storeProductBar) {
+        log.info("StoreProductBarServiceImpl.editStoreProductBar?storeProductBar={}", storeProductBar);
+        if (storeProductBar.getId() == null) {
+            log.error("更新酒吧商品失败:ID不能为空");
+            return R.fail("ID不能为空");
+        }
+
+        // 设置更新人
+        if (storeProductBar.getUpdatedUserId() == null) {
+            storeProductBar.setUpdatedUserId(0);
+        }
+
+        boolean result = this.updateById(storeProductBar);
+        if (result) {
+            return R.data(storeProductBar);
+        }
+        return R.fail("修改失败");
+    }
+
+    @Override
+    public R<Boolean> deleteStoreProductBar(Integer id) {
+        log.info("StoreProductBarServiceImpl.deleteStoreProductBar?id={}", id);
+        boolean result = this.removeById(id);
+        if (result) {
+            return R.success("删除成功");
+        }
+        return R.fail("删除失败");
+    }
+
+    @Override
+    public R<StoreProductBar> getStoreProductBarById(Integer id) {
+        log.info("StoreProductBarServiceImpl.getStoreProductBarById?id={}", id);
+        StoreProductBar storeProductBar = this.getById(id);
+        if (storeProductBar != null) {
+            return R.data(storeProductBar);
+        }
+        return R.fail("查询失败,数据不存在");
+    }
+
+    @Override
+    public IPage<StoreProductBar> getPage(int pageNum, int pageSize, String name, String category, Integer status, Integer extId) {
+        LambdaQueryWrapper<StoreProductBar> queryWrapper = new LambdaQueryWrapper<>();
+
+        // 名称模糊查询
+        if (StringUtils.hasText(name)) {
+            queryWrapper.like(StoreProductBar::getName, name);
+        }
+
+        // 品类查询
+        if (StringUtils.hasText(category)) {
+            queryWrapper.eq(StoreProductBar::getCategory, category);
+        }
+
+        // 状态查询
+        if (status != null) {
+            queryWrapper.eq(StoreProductBar::getStatus, status);
+        }
+
+        // 商品表主键查询
+        if (extId != null) {
+            queryWrapper.eq(StoreProductBar::getExtId, extId);
+        }
+
+        // 按创建时间倒序
+        queryWrapper.orderByDesc(StoreProductBar::getCreatedTime);
+
+        return this.page(new Page<>(pageNum, pageSize), queryWrapper);
+    }
+
+    @Override
+    public List<StoreProductBar> getListByExtId(Integer extId) {
+        if (extId == null) {
+            return null;
+        }
+        LambdaQueryWrapper<StoreProductBar> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(StoreProductBar::getExtId, extId)
+                .orderByDesc(StoreProductBar::getCreatedTime);
+        return this.list(queryWrapper);
+    }
+
+    @Override
+    public List<StoreProductBar> getListByCategory(String category) {
+        if (!StringUtils.hasText(category)) {
+            return null;
+        }
+        LambdaQueryWrapper<StoreProductBar> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(StoreProductBar::getCategory, category)
+                .orderByDesc(StoreProductBar::getCreatedTime);
+        return this.list(queryWrapper);
+    }
+
+    @Override
+    public boolean updateStatus(Integer id, Integer status) {
+        if (id == null) {
+            log.error("更新酒吧商品状态失败:ID不能为空");
+            return false;
+        }
+        if (status == null || (status != 0 && status != 1)) {
+            log.error("更新酒吧商品状态失败:状态值无效,只能为0或1");
+            return false;
+        }
+
+        LambdaUpdateWrapper<StoreProductBar> updateWrapper = new LambdaUpdateWrapper<>();
+        updateWrapper.eq(StoreProductBar::getId, id)
+                .set(StoreProductBar::getStatus, status);
+
+        return this.update(updateWrapper);
+    }
+
+    @Override
+    public boolean deleteBatch(List<Integer> ids) {
+        if (ids == null || ids.isEmpty()) {
+            log.error("批量删除酒吧商品失败:ID列表不能为空");
+            return false;
+        }
+        // 逻辑删除,MyBatis-Plus会自动处理
+        return this.removeByIds(ids);
+    }
+
+    @Override
+    public List<StoreProductBar> getByExtId(Integer id) {
+        return this.lambdaQuery().eq(StoreProductBar::getExtId, id).list();
+    }
+}

+ 176 - 0
alien-store/src/main/java/shop/alien/store/service/impl/StoreProductDelicaciesServiceImpl.java

@@ -0,0 +1,176 @@
+package shop.alien.store.service.impl;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import lombok.RequiredArgsConstructor;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+import org.springframework.util.StringUtils;
+import shop.alien.entity.store.StoreProductDelicacies;
+import shop.alien.mapper.StoreProductDelicaciesMapper;
+import shop.alien.store.service.StoreProductDelicaciesService;
+
+import java.util.List;
+
+/**
+ * 美食商品表 服务实现类
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+@Slf4j
+@Service
+@RequiredArgsConstructor
+@Transactional
+public class StoreProductDelicaciesServiceImpl implements StoreProductDelicaciesService {
+
+    private final StoreProductDelicaciesMapper storeProductDelicaciesMapper;
+
+    @Override
+    public IPage<StoreProductDelicacies> getPage(int pageNum, int pageSize, String name, String category, String extGroup, Integer status, Integer extId) {
+        LambdaQueryWrapper<StoreProductDelicacies> queryWrapper = new LambdaQueryWrapper<>();
+
+        // 名称模糊查询
+        if (StringUtils.hasText(name)) {
+            queryWrapper.like(StoreProductDelicacies::getName, name);
+        }
+
+        // 类别查询
+        if (StringUtils.hasText(category)) {
+            queryWrapper.eq(StoreProductDelicacies::getCategory, category);
+        }
+
+        // 菜品分组查询
+        if (StringUtils.hasText(extGroup)) {
+            queryWrapper.eq(StoreProductDelicacies::getExtGroup, extGroup);
+        }
+
+        // 状态查询
+        if (status != null) {
+            queryWrapper.eq(StoreProductDelicacies::getStatus, status);
+        }
+
+        // 商品表主键查询
+        if (extId != null) {
+            queryWrapper.eq(StoreProductDelicacies::getExtId, extId);
+        }
+
+        // 按创建时间倒序
+        queryWrapper.orderByDesc(StoreProductDelicacies::getCreatedTime);
+
+        return storeProductDelicaciesMapper.selectPage(new Page<>(pageNum, pageSize), queryWrapper);
+    }
+
+    @Override
+    public StoreProductDelicacies getById(Integer id) {
+        return storeProductDelicaciesMapper.selectById(id);
+    }
+
+    @Override
+    public boolean saveDelicacies(StoreProductDelicacies delicacies) {
+        // 设置默认值
+        if (delicacies.getUnit() == null || delicacies.getUnit().isEmpty()) {
+            delicacies.setUnit("份");
+        }
+        if (delicacies.getQuantity() == null) {
+            delicacies.setQuantity(0);
+        }
+        if (delicacies.getStatus() == null) {
+            delicacies.setStatus(1);
+        }
+        if (delicacies.getCreatedUserId() == null) {
+            delicacies.setCreatedUserId(0);
+        }
+        if (delicacies.getUpdatedUserId() == null) {
+            delicacies.setUpdatedUserId(0);
+        }
+
+        return storeProductDelicaciesMapper.insert(delicacies) > 0;
+    }
+
+    @Override
+    public boolean updateDelicacies(StoreProductDelicacies delicacies) {
+        if (delicacies.getId() == null) {
+            log.error("更新美食商品失败:ID不能为空");
+            return false;
+        }
+
+        // 设置更新人
+        if (delicacies.getUpdatedUserId() == null) {
+            delicacies.setUpdatedUserId(0);
+        }
+
+        return storeProductDelicaciesMapper.updateById(delicacies) > 0;
+    }
+
+    @Override
+    public boolean deleteDelicacies(Integer id) {
+        // 逻辑删除,MyBatis-Plus会自动处理
+        return storeProductDelicaciesMapper.deleteById(id) > 0;
+    }
+
+    @Override
+    public boolean deleteBatch(List<Integer> ids) {
+        if (ids == null || ids.isEmpty()) {
+            log.error("批量删除美食商品失败:ID列表不能为空");
+            return false;
+        }
+        // 逻辑删除,MyBatis-Plus会自动处理
+        return storeProductDelicaciesMapper.deleteBatchIds(ids) > 0;
+    }
+
+    @Override
+    public boolean updateStatus(Integer id, Integer status) {
+        if (id == null) {
+            log.error("更新美食商品状态失败:ID不能为空");
+            return false;
+        }
+        if (status == null || (status != 0 && status != 1)) {
+            log.error("更新美食商品状态失败:状态值无效,只能为0或1");
+            return false;
+        }
+
+        LambdaUpdateWrapper<StoreProductDelicacies> updateWrapper = new LambdaUpdateWrapper<>();
+        updateWrapper.eq(StoreProductDelicacies::getId, id)
+                .set(StoreProductDelicacies::getStatus, status);
+
+        return storeProductDelicaciesMapper.update(null, updateWrapper) > 0;
+    }
+
+    @Override
+    public List<StoreProductDelicacies> getListByExtId(Integer extId) {
+        if (extId == null) {
+            return null;
+        }
+        LambdaQueryWrapper<StoreProductDelicacies> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(StoreProductDelicacies::getExtId, extId)
+                .orderByDesc(StoreProductDelicacies::getCreatedTime);
+        return storeProductDelicaciesMapper.selectList(queryWrapper);
+    }
+
+    @Override
+    public List<StoreProductDelicacies> getListByCategory(String category) {
+        if (!StringUtils.hasText(category)) {
+            return null;
+        }
+        LambdaQueryWrapper<StoreProductDelicacies> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(StoreProductDelicacies::getCategory, category)
+                .orderByDesc(StoreProductDelicacies::getCreatedTime);
+        return storeProductDelicaciesMapper.selectList(queryWrapper);
+    }
+
+    @Override
+    public List<StoreProductDelicacies> getListByExtGroup(String extGroup) {
+        if (!StringUtils.hasText(extGroup)) {
+            return null;
+        }
+        LambdaQueryWrapper<StoreProductDelicacies> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(StoreProductDelicacies::getExtGroup, extGroup)
+                .orderByDesc(StoreProductDelicacies::getCreatedTime);
+        return storeProductDelicaciesMapper.selectList(queryWrapper);
+    }
+}
+

+ 164 - 0
alien-store/src/main/java/shop/alien/store/service/impl/StoreProductGymServiceImpl.java

@@ -0,0 +1,164 @@
+package shop.alien.store.service.impl;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
+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.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+import org.springframework.util.StringUtils;
+import shop.alien.entity.result.R;
+import shop.alien.entity.store.StoreProductGym;
+import shop.alien.mapper.StoreProductGymMapper;
+import shop.alien.store.service.StoreProductGymService;
+
+import java.util.List;
+
+/**
+ * 运动健身商品表 服务实现类
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+@Slf4j
+@Transactional
+@Service
+@RequiredArgsConstructor
+public class StoreProductGymServiceImpl extends ServiceImpl<StoreProductGymMapper, StoreProductGym> implements StoreProductGymService {
+
+    @Override
+    public R<StoreProductGym> addStoreProductGym(StoreProductGym storeProductGym) {
+        log.info("StoreProductGymServiceImpl.addStoreProductGym?storeProductGym={}", storeProductGym);
+        // 设置默认值
+        if (storeProductGym.getPrice() == null) {
+            storeProductGym.setPrice(new java.math.BigDecimal("0.00"));
+        }
+        if (storeProductGym.getStatus() == null) {
+            storeProductGym.setStatus(1);
+        }
+        if (storeProductGym.getCreatedUserId() == null) {
+            storeProductGym.setCreatedUserId(0);
+        }
+        if (storeProductGym.getUpdatedUserId() == null) {
+            storeProductGym.setUpdatedUserId(0);
+        }
+
+        boolean result = this.save(storeProductGym);
+        if (result) {
+            return R.data(storeProductGym);
+        }
+        return R.fail("新增失败");
+    }
+
+    @Override
+    public R<StoreProductGym> editStoreProductGym(StoreProductGym storeProductGym) {
+        log.info("StoreProductGymServiceImpl.editStoreProductGym?storeProductGym={}", storeProductGym);
+        if (storeProductGym.getId() == null) {
+            log.error("更新运动健身商品失败:ID不能为空");
+            return R.fail("ID不能为空");
+        }
+
+        // 设置更新人
+        if (storeProductGym.getUpdatedUserId() == null) {
+            storeProductGym.setUpdatedUserId(0);
+        }
+
+        boolean result = this.updateById(storeProductGym);
+        if (result) {
+            return R.data(storeProductGym);
+        }
+        return R.fail("修改失败");
+    }
+
+    @Override
+    public R<Boolean> deleteStoreProductGym(Integer id) {
+        log.info("StoreProductGymServiceImpl.deleteStoreProductGym?id={}", id);
+        boolean result = this.removeById(id);
+        if (result) {
+            return R.success("删除成功");
+        }
+        return R.fail("删除失败");
+    }
+
+    @Override
+    public R<StoreProductGym> getStoreProductGymById(Integer id) {
+        log.info("StoreProductGymServiceImpl.getStoreProductGymById?id={}", id);
+        StoreProductGym storeProductGym = this.getById(id);
+        if (storeProductGym != null) {
+            return R.data(storeProductGym);
+        }
+        return R.fail("查询失败,数据不存在");
+    }
+
+    @Override
+    public IPage<StoreProductGym> getPage(int pageNum, int pageSize, String name, String classMode, Integer status, Integer extId) {
+        LambdaQueryWrapper<StoreProductGym> queryWrapper = new LambdaQueryWrapper<>();
+
+        // 名称模糊查询
+        if (StringUtils.hasText(name)) {
+            queryWrapper.like(StoreProductGym::getName, name);
+        }
+
+        // 上课形式查询
+        if (StringUtils.hasText(classMode)) {
+            queryWrapper.eq(StoreProductGym::getClassMode, classMode);
+        }
+
+        // 状态查询
+        if (status != null) {
+            queryWrapper.eq(StoreProductGym::getStatus, status);
+        }
+
+        // 商品表主键查询
+        if (extId != null) {
+            queryWrapper.eq(StoreProductGym::getExtId, extId);
+        }
+
+        // 按创建时间倒序
+        queryWrapper.orderByDesc(StoreProductGym::getCreatedTime);
+
+        return this.page(new Page<>(pageNum, pageSize), queryWrapper);
+    }
+
+    @Override
+    public List<StoreProductGym> getListByExtId(Integer extId) {
+        if (extId == null) {
+            return null;
+        }
+        LambdaQueryWrapper<StoreProductGym> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(StoreProductGym::getExtId, extId)
+                .orderByDesc(StoreProductGym::getCreatedTime);
+        return this.list(queryWrapper);
+    }
+
+    @Override
+    public boolean updateStatus(Integer id, Integer status) {
+        if (id == null) {
+            log.error("更新运动健身商品状态失败:ID不能为空");
+            return false;
+        }
+        if (status == null || (status != 0 && status != 1)) {
+            log.error("更新运动健身商品状态失败:状态值无效,只能为0或1");
+            return false;
+        }
+
+        LambdaUpdateWrapper<StoreProductGym> updateWrapper = new LambdaUpdateWrapper<>();
+        updateWrapper.eq(StoreProductGym::getId, id)
+                .set(StoreProductGym::getStatus, status);
+
+        return this.update(updateWrapper);
+    }
+
+    @Override
+    public boolean deleteBatch(List<Integer> ids) {
+        if (ids == null || ids.isEmpty()) {
+            log.error("批量删除运动健身商品失败:ID列表不能为空");
+            return false;
+        }
+        // 逻辑删除,MyBatis-Plus会自动处理
+        return this.removeByIds(ids);
+    }
+}

+ 143 - 0
alien-store/src/main/java/shop/alien/store/service/impl/StoreProductItemServiceImpl.java

@@ -0,0 +1,143 @@
+package shop.alien.store.service.impl;
+
+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.springframework.beans.BeanUtils;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import shop.alien.entity.result.CommonEnum;
+import shop.alien.entity.result.R;
+import shop.alien.entity.store.StoreProductBar;
+import shop.alien.entity.store.StoreProductItem;
+import shop.alien.entity.store.vo.StoreProductItemGymVo;
+import shop.alien.entity.store.dto.StoreProductItemDto;
+import shop.alien.mapper.StoreProductItemMapper;
+import shop.alien.store.service.StoreProductBarService;
+import shop.alien.store.service.StoreProductItemService;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+
+/**
+ * 商品表 服务实现类
+ *
+ * @author system
+ * @since 2025-01-XX
+ */
+@Slf4j
+@Transactional(rollbackFor = Exception.class)
+@Service
+@RequiredArgsConstructor
+public class StoreProductItemServiceImpl extends ServiceImpl<StoreProductItemMapper, StoreProductItem> implements StoreProductItemService {
+
+    private final ObjectMapper objectMapper;
+
+    private final StoreProductBarService storeProductBarService;
+
+    @Override
+    public R<StoreProductItem> addStoreProductItemDto(StoreProductItemDto storeProductItemDto) {
+        log.info("StoreProductItemServiceImpl.addStoreProductItem?storeProductItem={}", storeProductItemDto);
+        StoreProductItem storeProductItem = new StoreProductItem();
+        BeanUtils.copyProperties(storeProductItemDto,storeProductItem);
+        // 设置pid默认值为0
+        storeProductItem.setPid(0);
+        // MySQL 驱动开启 useGeneratedKeys(Spring Boot 默认开启,通常不用改)。
+        this.save(storeProductItem);
+        // 添加套餐时,需要前端在子集合内元素分别设置type
+        // 处理子项(判空)
+        List<?> rawSubList = storeProductItemDto.getSubList();
+        if (rawSubList != null && !rawSubList.isEmpty()) {
+            List<StoreProductBar> subList = rawSubList.stream()
+                    .map(v -> objectMapper.convertValue(v, StoreProductBar.class))
+                    .collect(Collectors.toList());
+            Integer parentId = storeProductItem.getId();
+            subList.forEach(v -> v.setExtId(parentId));
+            boolean subSaved = storeProductBarService.saveBatch(subList);
+            if (!subSaved) {
+                throw new RuntimeException("子项保存失败");
+            }
+        }
+        return R.data(storeProductItem);
+    }
+
+    @Override
+    public R<StoreProductItem> editStoreProductItem(StoreProductItemDto storeProductItemDto) {
+        log.info("StoreProductItemServiceImpl.editStoreProductItem?storeProductItem={}", storeProductItemDto);
+        StoreProductItem storeProductItem = new StoreProductItem();
+        BeanUtils.copyProperties(storeProductItemDto,storeProductItem);
+        this.updateById(storeProductItem);
+        // 添加套餐时,需要前端在子集合内元素分别设置type
+        // 处理子项(判空)
+        List<?> rawSubList = storeProductItemDto.getSubList();
+        if (rawSubList != null && !rawSubList.isEmpty()) {
+            List<StoreProductBar> subList = rawSubList.stream()
+                    .map(v -> objectMapper.convertValue(v, StoreProductBar.class))
+                    .collect(Collectors.toList());
+            Integer parentId = storeProductItem.getId();
+            subList.forEach(v -> v.setExtId(parentId));
+            boolean subSaved = storeProductBarService.saveBatch(subList);
+            if (!subSaved) {
+                throw new RuntimeException("子项保存失败");
+            }
+        }
+        return R.data(storeProductItem);
+    }
+
+    @Override
+    public R<Boolean> deleteStoreProductItem(Integer id) {
+        log.info("StoreProductItemServiceImpl.deleteStoreProductItem?id={}", id);
+        boolean result = this.removeById(id);
+        if (result) {
+            return R.success("删除成功");
+        }
+        return R.fail("删除失败");
+    }
+
+    @Override
+    public R<List<StoreProductItemDto>> getStoreProductItemById(Integer id) {
+        log.info("StoreProductItemServiceImpl.getStoreProductItemById?id={}", id);
+        StoreProductItem storeProductItem = this.getById(id);
+        ArrayList<StoreProductItemDto> list = new ArrayList<>();
+        StoreProductItemDto storeProductItemDto = new StoreProductItemDto();
+        list.add(storeProductItemDto);
+        BeanUtils.copyProperties(storeProductItem,storeProductItemDto);
+        if (CommonEnum.StoreProductItemProdType.DELICACY_FOOD.getCode() == storeProductItem.getProdType()) {
+            list = this.getBaseMapper().getByPId(id);
+        }else {
+            List<StoreProductBar> barList = storeProductBarService.getByExtId(id);
+            storeProductItemDto.setSubList(barList);
+        }
+        return R.data(list);
+    }
+
+    @Override
+    public IPage<StoreProductItemGymVo> getPageWithGym(int pageNum, int pageSize, Integer storeId, String prodName, Integer prodType) {
+        log.info("StoreProductItemServiceImpl.getPageWithGym?pageNum={}, pageSize={}, storeId={}, prodName={}, prodType={}",
+                pageNum, pageSize, storeId, prodName, prodType);
+        Page<StoreProductItemGymVo> page = new Page<>(pageNum, pageSize);
+        if(prodType == 0){
+            return baseMapper.getPageWithGym(page, storeId, prodName, null);
+        }else{
+            return baseMapper.getPageWithGym(page, storeId, prodName, prodType);
+        }
+    }
+
+    @Override
+    public R<StoreProductItemGymVo> getDetailWithGym(Long id) {
+        log.info("StoreProductItemServiceImpl.getDetailWithGym?id={}", id);
+        if (id == null) {
+            return R.fail("ID不能为空");
+        }
+        StoreProductItemGymVo detail = baseMapper.getDetailWithGym(id);
+        if (detail != null) {
+            return R.data(detail);
+        }
+        return R.fail("查询失败,数据不存在");
+    }
+}
+