Compare commits

29 Commits

Author SHA1 Message Date
24ea4bfc32 Merge branch 'prod' into test
# Conflicts:
#	cash-service/order-service/src/main/java/com/czg/service/order/print/PrinterImpl.java
2026-05-18 09:52:02 +08:00
0a0f6d53bc 后厨单 2026-05-13 09:02:15 +08:00
2ddd4ba481 商品重量 2026-05-08 15:55:13 +08:00
79aeec76b7 商品重量 2026-05-08 15:53:46 +08:00
d9d95da453 商品 批量操作 2026-05-06 11:10:23 +08:00
962e6d7a0c Merge branch 'prod' into test 2026-05-06 09:30:39 +08:00
2ea8b3364c 菜单 pid 设置null问题 2026-04-29 16:24:19 +08:00
65ecd52a55 挂账人 时间 空值问题 2026-04-29 15:59:33 +08:00
4f7aae3840 分组列表增加 商品列表字段 2026-04-29 13:40:19 +08:00
e9d02bee0c 分组列表增加 商品列表字段 2026-04-29 13:36:14 +08:00
2977157b26 拖动排序 2026-04-28 17:40:02 +08:00
e823cb7e6b 拖动排序 2026-04-28 17:37:50 +08:00
d8b8b55e7a 挂账人 状态 2026-04-28 16:57:02 +08:00
06c6dc3e83 挂账人 创建时间 2026-04-28 16:23:05 +08:00
5db54ade5f 按照订单还款 用户余额问题 2026-04-28 16:14:32 +08:00
cdc2d770ec 挂账订单 创建时间 2026-04-28 15:59:16 +08:00
04ed3a5f5b 商品修改 商品分组 2026-04-28 15:58:32 +08:00
36687abe0f 挂账接口 2026-04-28 15:37:11 +08:00
2bb520d346 挂账接口 2026-04-28 15:11:52 +08:00
ab7598d706 挂账接口 2026-04-28 15:03:16 +08:00
1d3fce4523 已领取详情 2026-04-28 10:32:53 +08:00
c507df067b 已领取详情 2026-04-28 10:28:07 +08:00
db308e2e26 小票logo 改名为 标签打印logo 2026-04-28 10:27:23 +08:00
680684e31a 商品售罄开关 2026-04-27 17:23:01 +08:00
604a42fa4d 重置统计数据 2026-04-27 16:55:23 +08:00
880d19b0fa 修改值问题 2026-04-27 14:04:59 +08:00
772ba6376a 厨房小票二维码打印开关 2026-04-27 11:48:48 +08:00
b1a39167ac 员工角色 名称 2026-04-27 11:32:35 +08:00
61e1aeb16a 店铺签约 2026-04-27 11:09:53 +08:00
59 changed files with 669 additions and 786 deletions

View File

@@ -1,54 +0,0 @@
package com.czg.controller.admin;
import com.czg.account.dto.PageDTO;
import com.czg.account.dto.register.MerchantRegisterDTO;
import com.czg.account.entity.MerchantRegister;
import com.czg.account.service.MerchantRegisterService;
import com.czg.annotation.SaAdminCheckPermission;
import com.czg.annotation.SaAdminCheckRole;
import com.czg.resp.CzgResult;
import com.mybatisflex.core.paginate.Page;
import jakarta.annotation.Resource;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
/**
* 激活码管理
* @author Administrator
*/
@RestController
@RequestMapping("/admin/merchantRegister")
public class MerchantRegisterController {
@Resource
private MerchantRegisterService merchantRegisterService;
/**
* 激活码列表
* 权限标识: merchantRegister:list
* @param pageDTO 分页参数
* @param state 状态 0未激活 1已激活
* @param startTime 开始时间
* @param endTime 结束时间
* @return 激活码列表
*/
@SaAdminCheckRole("管理员")
@SaAdminCheckPermission(parentName = "激活码", value = "merchantRegister:list", name = "激活码列表")
@GetMapping
public CzgResult<Page<MerchantRegister>> get(PageDTO pageDTO, Integer state, String startTime, String endTime) {
return CzgResult.success(merchantRegisterService.get(pageDTO, state, startTime, endTime));
}
/**
* 生成激活码
* 权限标识: merchantRegister:add
* @param merchantRegisterDTO 激活码信息
* @return 是否成功
*/
@SaAdminCheckRole("管理员")
@SaAdminCheckPermission(parentName = "激活码", value = "merchantRegister:add", name = "生成激活码")
@PostMapping
public CzgResult<Boolean> add(@RequestBody @Validated MerchantRegisterDTO merchantRegisterDTO) {
return CzgResult.success(merchantRegisterService.add(merchantRegisterDTO));
}
}

View File

@@ -5,8 +5,10 @@ import com.czg.account.dto.shopinfo.ShopBranchSelectDTO;
import com.czg.account.dto.shopinfo.ShopDetailDTO;
import com.czg.account.dto.shopinfo.ShopInfoAddDTO;
import com.czg.account.dto.shopinfo.ShopInfoEditDTO;
import com.czg.account.entity.ShopRegister;
import com.czg.account.entity.ShopInfo;
import com.czg.account.service.AuthorizationService;
import com.czg.account.service.ShopRegisterService;
import com.czg.account.service.ShopInfoService;
import com.czg.annotation.SaAdminCheckPermission;
import com.czg.annotation.SaAdminCheckRole;
@@ -32,6 +34,8 @@ public class ShopInfoController {
private ShopInfoService shopInfoService;
@Resource
private AuthorizationService authorizationService;
@Resource
private ShopRegisterService shopRegisterService;
/**
* 店铺列表, 只允许管理员调用
@@ -118,4 +122,17 @@ public class ShopInfoController {
return CzgResult.success();
}
/**
* 续期记录
*
* @param pageDTO 分页参数
* @return 续期记录列表
*/
@SaAdminCheckRole("管理员")
@GetMapping("/registerRecord")
public CzgResult<Page<ShopRegister>> get(PageDTO pageDTO, Long shopId) {
Page<ShopRegister> page = shopRegisterService.page(new Page<>(pageDTO.page(), pageDTO.size()),
new QueryWrapper().eq(ShopRegister::getShopId, shopId).orderBy(ShopRegister::getCreateTime, false));
return CzgResult.success(page);
}
}

View File

@@ -18,6 +18,7 @@ import java.util.List;
/**
* 支付方式管理
*
* @author Administrator
*/
@RestController
@@ -60,7 +61,19 @@ public class ShopPayTypeController {
@PostMapping
public CzgResult<Boolean> add(@RequestBody @Validated(InsertGroup.class) ShopPayTypeAddDTO shopPayTypeAddDTO) {
ShopPayType shopPayType = BeanUtil.copyProperties(shopPayTypeAddDTO, ShopPayType.class);
return CzgResult.success(shopPayTypeService.add(StpKit.USER.getShopId(),shopPayType));
return CzgResult.success(shopPayTypeService.add(StpKit.USER.getShopId(), shopPayType));
}
/**
* 支付类型拖动排序
*
* @param shopId 店铺ID
* @param id 拖动的支付类型ID
* @param targetSort 目标位置排序号
*/
@GetMapping("/sort")
public CzgResult<Void> sort(@RequestParam Long shopId, @RequestParam Integer id, @RequestParam Integer targetSort) {
shopPayTypeService.updateSort(shopId, id, targetSort);
return CzgResult.success();
}
}

View File

@@ -24,7 +24,7 @@ public class UShopExtendController {
/**
* 根据key获取拓展信息
* @param shopId 店铺id
* @param autoKey key index_bg 首页 my_bg 个人中心 member_bg 会员卡 shopinfo_bg 商品列表 ticket_logo 小票logo
* @param autoKey key index_bg 首页 my_bg 个人中心 member_bg 会员卡 shopinfo_bg 商品列表 ticket_logo 标签打印logo
* @return 详细信息
*/
@GetMapping

View File

@@ -1,6 +1,7 @@
package com.czg.controller;
import com.czg.task.StatisticTask;
import com.czg.utils.FunUtils;
import jakarta.annotation.Resource;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
@@ -33,8 +34,10 @@ public class StatisticTaskController {
statisticTask.statisticAndInsertProd(shopId, date);
} else if ("table".equals(type)) {
statisticTask.statisticAndInsertTable(shopId, date);
} else {
return "未知错误";
} else if ("all".equals(type)) {
FunUtils.safeRunVoid(() -> statisticTask.statisticAndInsertOrder(shopId, date));
FunUtils.safeRunVoid(() -> statisticTask.statisticAndInsertProd(shopId, date));
FunUtils.safeRunVoid(() -> statisticTask.statisticAndInsertTable(shopId, date));
}
return "success";
}

View File

@@ -1,7 +1,7 @@
package com.czg.controller.admin;
import com.czg.log.annotation.OperationLog;
import com.czg.order.dto.CreditBuyerDTO;
import com.czg.order.entity.CreditBuyer;
import com.czg.order.param.CreditBuyerQueryParam;
import com.czg.order.param.CreditBuyerRepaymentParam;
import com.czg.order.service.CreditBuyerService;
@@ -31,8 +31,8 @@ public class CreditBuyerController {
@GetMapping("page")
@OperationLog("挂账人-分页")
//@SaAdminCheckPermission("creditBuyer:page")
public CzgResult<Page<CreditBuyerDTO>> getCreditBuyerPage(CreditBuyerQueryParam param) {
Page<CreditBuyerDTO> data = creditBuyerService.getCreditBuyerPage(param);
public CzgResult<Page<CreditBuyer>> getCreditBuyerPage(CreditBuyerQueryParam param) {
Page<CreditBuyer> data = creditBuyerService.getCreditBuyerPage(param);
return CzgResult.success(data);
}
@@ -43,10 +43,9 @@ public class CreditBuyerController {
@GetMapping("{id}")
@OperationLog("挂账人-详情")
//@SaAdminCheckPermission("creditBuyer:info")
public CzgResult<CreditBuyerDTO> getCreditBuyerById(@PathVariable("id") String id) {
public CzgResult<CreditBuyer> getCreditBuyerById(@PathVariable("id") String id) {
AssertUtil.isNull(id, "{}不能为空", "id");
CreditBuyerDTO data = creditBuyerService.getCreditBuyerById(id);
return CzgResult.success(data);
return CzgResult.success(creditBuyerService.getById(id));
}
/**
@@ -55,7 +54,7 @@ public class CreditBuyerController {
@PostMapping
@OperationLog("挂账人-新增")
//@SaAdminCheckPermission("creditBuyer:add")
public CzgResult<Void> addCreditBuyer(@RequestBody CreditBuyerDTO dto) {
public CzgResult<Void> addCreditBuyer(@RequestBody CreditBuyer dto) {
creditBuyerService.addCreditBuyer(dto);
return CzgResult.success();
}
@@ -66,7 +65,7 @@ public class CreditBuyerController {
@PutMapping
@OperationLog("挂账人-修改")
//@SaAdminCheckPermission("creditBuyer:update")
public CzgResult<Void> updateCreditBuyer(@RequestBody CreditBuyerDTO dto) {
public CzgResult<Void> updateCreditBuyer(@RequestBody CreditBuyer dto) {
creditBuyerService.updateCreditBuyer(dto);
return CzgResult.success();
}

View File

@@ -6,13 +6,18 @@ import com.czg.order.param.SaleSummaryCountParam;
import com.czg.order.service.FinanceStsService;
import com.czg.resp.CzgResult;
import com.czg.sa.StpKit;
import com.czg.task.StatisticTask;
import com.czg.utils.FunUtils;
import jakarta.annotation.Resource;
import jakarta.servlet.http.HttpServletResponse;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import java.time.LocalDate;
/**
* 管理端/财务报表
* @author yjjie
@@ -25,6 +30,30 @@ public class FinanceStsController {
@Resource
private FinanceStsService financeStsService;
@Resource
private StatisticTask statisticTask;
/**
* 基础统计 预留重置统计
*
* @param date 日期yyyy-MM-dd
*/
@GetMapping("/base")
public String baseStatistic(@RequestParam LocalDate date, @RequestParam Long shopId, @RequestParam String type) {
if ("order".equals(type)) {
statisticTask.statisticAndInsertOrder(shopId, date);
} else if ("prod".equals(type)) {
statisticTask.statisticAndInsertProd(shopId, date);
} else if ("table".equals(type)) {
statisticTask.statisticAndInsertTable(shopId, date);
} else if ("all".equals(type)) {
FunUtils.safeRunVoid(() -> statisticTask.statisticAndInsertOrder(shopId, date));
FunUtils.safeRunVoid(() -> statisticTask.statisticAndInsertProd(shopId, date));
FunUtils.safeRunVoid(() -> statisticTask.statisticAndInsertTable(shopId, date));
}
return "success";
}
/**
* 查询财务报表
*/

View File

@@ -63,7 +63,6 @@ public class ProductController {
* 商品-分页
*/
@GetMapping("page")
@OperationLog("商品-分页")
//@SaAdminCheckPermission("product:page")
public CzgResult<Map<String, Object>> getProductPage(ProductDTO param) {
Page<ProductDTO> data = productService.getProductPage(param);
@@ -83,7 +82,6 @@ public class ProductController {
* 商品-列表
*/
@GetMapping("list")
@OperationLog("商品-列表")
public CzgResult<List<ProductDTO>> getProductList(@RequestParam(required = false) Long categoryId) {
return CzgResult.success(productService.getProductCacheList(StpKit.USER.getShopId(), categoryId));
}
@@ -92,7 +90,6 @@ public class ProductController {
* 商品-详情
*/
@GetMapping("{id}")
@OperationLog("商品-详情")
//@SaAdminCheckPermission("product:info")
public CzgResult<ProductDTO> getProductById(@PathVariable("id") Long id) {
AssertUtil.isNull(id, "{}不能为空", "id");
@@ -242,7 +239,6 @@ public class ProductController {
* 商品-统计
*/
@GetMapping("statistics")
@OperationLog("商品-统计")
//@SaAdminCheckPermission("product:statistics")
public CzgResult<ProductStatisticsVo> statistics(ProductInfoParam param) {
Long shopId = StpKit.USER.getShopId(0L);
@@ -251,6 +247,17 @@ public class ProductController {
return CzgResult.success(data);
}
/**
* 商品-批量操作
*/
@GetMapping("batchOperate")
public CzgResult<Void> batchOperate(ProductBatchParam param) {
Long shopId = StpKit.USER.getShopId();
param.setShopId(shopId);
productService.batchOperate(param);
return CzgResult.success();
}
/**
* 商品-报损
*/

View File

@@ -5,7 +5,10 @@ import com.alibaba.fastjson2.JSONWriter;
import jakarta.annotation.Resource;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.redis.core.Cursor;
import org.springframework.data.redis.core.RedisCallback;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.ScanOptions;
import org.springframework.data.redis.core.script.DefaultRedisScript;
import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils;
@@ -52,6 +55,34 @@ public class RedisService {
return redisTemplate.delete(keys);
}
/**
* 删除某前缀Key
* @param prefix
*/
public void deleteKeysByPrefixSafe(String prefix) {
// 拼接匹配规则:前缀 + * → 比如传入 user → 匹配 user*
String pattern = prefix + "*";
// redisTemplate.execute使用 Redis 底层连接执行原生命令(性能更高)
redisTemplate.execute((RedisCallback<Void>) connection -> {
// try-with-resources自动关闭游标避免资源泄漏
try (Cursor<byte[]> cursor = connection.scan(
// SCAN 配置匹配规则、每次扫描1000条
ScanOptions.scanOptions().match(pattern).count(1000).build()
)) {
// 迭代遍历扫描到的所有 key
while (cursor.hasNext()) {
// 删除当前遍历到的 key
connection.del(cursor.next());
}
} catch (Exception e) {
// 异常捕获打印,避免删除失败导致程序报错
e.printStackTrace();
}
return null;
});
}
/**
* 指定缓存失效时间
*

View File

@@ -1,16 +0,0 @@
package com.czg.account.dto.register;
import jakarta.validation.constraints.Max;
import jakarta.validation.constraints.Min;
import jakarta.validation.constraints.NotNull;
public record MerchantRegisterDTO(
@NotNull(message = "激活时长不能为空")
@Min(1)
Integer periodMonth,
@NotNull(message = "数量不为空")
@Min(1)
@Max(10)
Integer num
) {
}

View File

@@ -4,6 +4,8 @@ import jakarta.validation.constraints.NotEmpty;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
import java.math.BigDecimal;
/**
* @author Administrator
*/
@@ -20,8 +22,14 @@ public class ShopInfoAddDTO {
private String frontImg;
@NotEmpty(message = "试用/正式不为空")
private String profiles;
// @NotEmpty(message = "激活码不为空")
private String activateCode;
/**
* 激活时长
*/
private Integer activateDuration;
/**
* 激活费用
*/
private BigDecimal activateAmount;
@NotEmpty(message = "登录账号不为空")
private String accountName;
@NotEmpty(message = "登录密码不为空")

View File

@@ -249,9 +249,13 @@ public class ShopInfoEditDTO {
private String taxAmount;
/**
* 店铺激活码
* 激活时长
*/
private String activateCode;
private Integer activateDuration;
/**
* 激活费用
*/
private BigDecimal activateAmount;
/**
* 是否为主店 1-是 0-否
*/
@@ -288,6 +292,10 @@ public class ShopInfoEditDTO {
* 数签子
*/
private Integer isCountStick;
/**
* 后厨单菜二维码
*/
private Integer isKitchenCode;
/**
* 退菜退库存模式 1跟随商品分类 2 跟随单商品
*/

View File

@@ -135,6 +135,10 @@ public class ShopConfig implements Serializable {
* 数签子
*/
private Integer isCountStick;
/**
* 后厨单菜二维码
*/
private Integer isKitchenCode;
/**
* 退菜退库存模式 1跟随商品分类 2 跟随单商品
*/

View File

@@ -104,7 +104,7 @@ public class ShopExtend implements Serializable {
this.value = "https://czg-qr-order.oss-cn-beijing.aliyuncs.com/shopDetails/topBanner.png";
break;
case "ticket_logo":
this.name = "小票logo";
this.name = "标签打印logo";
this.detail="建议尺寸: 417*139";
this.value = "https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/20241022/eeee8e85c66947e5bcaebf687381b5d6.png";
break;

View File

@@ -361,6 +361,11 @@ public class ShopInfo implements Serializable {
*/
@Column(ignore = true)
private Integer isCountStick;
/**
* 后厨单菜二维码
*/
@Column(ignore = true)
private Integer isKitchenCode;
/**
* 退菜退库存模式 1跟随商品分类 2 跟随单商品
*/

View File

@@ -37,6 +37,12 @@ public class ShopPayType implements Serializable {
@Id(keyType = KeyType.Auto)
private Integer id;
/**
* 图标
*/
private String icon;
/**
* 支付类型cash,alipay,weixin,deposit,arrears,virtual,member-account
*/
@@ -57,26 +63,6 @@ public class ShopPayType implements Serializable {
*/
private Long shopId;
/**
* 0允许退款 1-不允许退款
*/
private Integer isRefundable;
/**
* 是否打开钱箱
*/
private Integer isOpenCashDrawer;
/**
* 0不是 1是 [系统级支付]
*/
private Integer isSystem;
/**
* 0-非虚拟 1虚拟 virtual
*/
private Integer isIdeal;
/**
* 0-不显示1显示
*/
@@ -91,10 +77,4 @@ public class ShopPayType implements Serializable {
private LocalDateTime createTime;
@Column(onInsertValue = "now()")
private LocalDateTime updateTime;
/**
* 图标
*/
private String icon;
}

View File

@@ -14,7 +14,7 @@ import java.math.BigDecimal;
import java.time.LocalDateTime;
/**
* 激活码 实体类
* 店铺签约 实体类
*
* @author Administrator
* @since 2025-02-11
@@ -23,8 +23,8 @@ import java.time.LocalDateTime;
@NoArgsConstructor
@AllArgsConstructor
@Table("tb_merchant_register")
public class MerchantRegister implements Serializable {
@Table("tb_shop_register")
public class ShopRegister implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
@@ -32,18 +32,13 @@ public class MerchantRegister implements Serializable {
@Id(keyType = KeyType.Auto)
private Integer id;
/**
* 激活码
*/
private String registerCode;
/**
* 店铺id
*/
private Long shopId;
/**
* 激活码金额
* 店铺签约金额
*/
private BigDecimal amount;
@@ -52,11 +47,6 @@ public class MerchantRegister implements Serializable {
*/
private Integer periodMonth;
/**
* 状态0未使用1已使用
*/
private Integer status;
/**
* 创建时间
*/

View File

@@ -89,6 +89,8 @@ public class ShopStaff implements Serializable {
@Column(ignore = true)
private Long roleId;
@Column(ignore = true)
private String roleName;
@Column(ignore = true)
private String accountName;
@Column(ignore = true)
private String accountPwd;

View File

@@ -1,20 +0,0 @@
package com.czg.account.service;
import com.czg.account.dto.PageDTO;
import com.czg.account.dto.register.MerchantRegisterDTO;
import com.czg.account.entity.MerchantRegister;
import com.mybatisflex.core.paginate.Page;
import com.mybatisflex.core.service.IService;
/**
* 激活码 服务层。
*
* @author Administrator
* @since 2025-02-11
*/
public interface MerchantRegisterService extends IService<MerchantRegister> {
Page<MerchantRegister> get(PageDTO pageDTO, Integer state, String startTime, String endTime);
Boolean add(MerchantRegisterDTO merchantRegisterDTO);
}

View File

@@ -21,4 +21,12 @@ public interface ShopPayTypeService extends IService<ShopPayType> {
Boolean edit(Long shopId, ShopPayTypeDTO shopPayTypeDTO);
void addInfo(Long shopId);
/**
* 拖动排序
* @param shopId 店铺ID
* @param payTypeId 当前拖动的支付类型ID
* @param targetSort 目标排序号
*/
void updateSort(Long shopId, Integer payTypeId, Integer targetSort);
}

View File

@@ -0,0 +1,14 @@
package com.czg.account.service;
import com.czg.account.entity.ShopRegister;
import com.mybatisflex.core.service.IService;
/**
* 店铺签约 服务层。
*
* @author Administrator
* @since 2025-02-11
*/
public interface ShopRegisterService extends IService<ShopRegister> {
}

View File

@@ -1,6 +1,6 @@
package com.czg.account.vo;
import com.czg.account.entity.MerchantRegister;
import com.czg.account.entity.ShopRegister;
import lombok.Data;
import lombok.EqualsAndHashCode;
@@ -11,7 +11,7 @@ import java.time.LocalDateTime;
*/
@EqualsAndHashCode(callSuper = true)
@Data
public class MerchantRegisterVO extends MerchantRegister {
public class ShopRegisterVO extends ShopRegister {
private String shopName;
private String phone;
private String registerType;

View File

@@ -1,153 +0,0 @@
package com.czg.order.dto;
import java.io.Serializable;
import java.time.LocalDateTime;
import com.alibaba.fastjson2.annotation.JSONField;
import java.io.Serial;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* 店铺小票打印记录 实体类。
*
* @author zs
* @since 2025-03-11
*/
@Data
@NoArgsConstructor
@AllArgsConstructor
public class PrintMachineLogDTO implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
/**
* id
*/
private Long id;
/**
* 打印机类型 本地打印机-local USB打印机-USB 云打印机-network
*/
private String connectionType;
/**
* 打印机品牌 云想印 = yxyPrinter飞鹅 = fePrinter 本地 = local USB = printer
*/
private String contentType;
/**
* 打印小票 标签-label 出品-kitchen 小票-cash
*/
private String subType;
/**
* 打印机名称
*/
private String name;
/**
* IP地址/打印机编号
*/
private String address;
/**
* 端口/打印机秘钥
*/
private String port;
/**
* 小票尺寸 58mm 80mm
*/
private String receiptSize;
/**
* 分类打印 0-所以 1-部分分类 2-部分商品
*/
private String classifyPrint;
/**
* 桌台打印 0-所有 1-部分
*/
private String tablePrint;
/**
* 打印数量 c1m1^2=顾客+商家[2张] m1^1=商家[1张] c1^1顾客[1张] c2m1^3=顾客2+商家1[3张]
*/
private String printQty;
/**
* 打印方式 normal-普通出单 one-一菜一品 callTicket-排队取号
*/
private String printMethod;
/**
* 打印类型 JSON数组字符串数据 1-确认退款单 2-交班单 3-排队取号,如:[1,2,3]
*/
private String printType;
/**
* 打印票据 0-全部打印 1-仅厨房 2-仅前台
*/
private String printReceipt;
/**
* 打印内容
*/
private String printContent;
/**
* 店铺id
*/
private String shopId;
/**
* 业务类型
*/
private String bizType;
/**
* 打印人id
*/
private Long createUserId;
/**
* 打印人名称
*/
private String createUserName;
/**
* 打印任务创建时间
*/
@JSONField(format = "yyyy-MM-dd HH:mm:ss")
private LocalDateTime createTime;
/**
* 打印任务id用于复查打印状态云想印=orderId
*/
private String taskId;
/**
* 实际打印时间
*/
@JSONField(format = "yyyy-MM-dd HH:mm:ss")
private LocalDateTime printTime;
/**
* 失败标识 1-是 0-否
*/
private Integer failFlag;
/**
* 响应代码
*/
private String respCode;
/**
* 响应消息
*/
private String respMsg;
}

View File

@@ -1,5 +1,6 @@
package com.czg.order.entity;
import com.mybatisflex.annotation.Column;
import com.mybatisflex.annotation.Id;
import com.mybatisflex.annotation.KeyType;
import com.mybatisflex.annotation.Table;
@@ -9,6 +10,7 @@ import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
import java.math.BigDecimal;
import java.time.LocalDateTime;
/**
* 挂账人
@@ -76,4 +78,16 @@ public class CreditBuyer implements Serializable {
* 删除标志 0-正常 1-删除
*/
private Integer isDel;
/**
* 还款提醒日 最大28
*/
private Integer expireRemindDay;
/**
* 还款提醒 提醒多久以前的数据 暂定单位 月
*/
private Integer expireRemind;
@Column(onInsertValue = "now()")
private LocalDateTime createTime;
}

View File

@@ -1,5 +1,6 @@
package com.czg.order.entity;
import com.mybatisflex.annotation.Column;
import com.mybatisflex.annotation.Id;
import com.mybatisflex.annotation.KeyType;
import com.mybatisflex.annotation.Table;
@@ -36,10 +37,18 @@ public class CreditBuyerOrder implements Serializable {
* 挂账人编码
*/
private String creditBuyerId;
/**
* 订单金额
*/
private BigDecimal orderAmount;
/**
* 已付金额
*/
private BigDecimal paidAmount;
/**
* 退款金额
*/
private BigDecimal refundAmount;
/**
* 状态 unpaid-未付款 partial-部分支付 paid-已付款
*/
@@ -56,4 +65,6 @@ public class CreditBuyerOrder implements Serializable {
* 备注
*/
private String remark;
@Column(onInsertValue = "now()")
private LocalDateTime createTime;
}

View File

@@ -1,6 +1,7 @@
package com.czg.order.param;
import com.alibaba.fastjson2.annotation.JSONField;
import com.czg.utils.CzgStrUtils;
import lombok.Data;
import java.io.Serial;
@@ -23,24 +24,39 @@ public class CreditBuyerQueryParam implements Serializable {
@JSONField(serialize = false)
private String id;
/**
* 关键字
* 挂账人
*/
private String keywords;
private String debtor;
/**
* 还款状态 unpaid-未还款 partial-部分还款 paid-已还清
* 手机号
*/
private String repaymentStatus;
/**
* 责任人
*/
private String responsiblePerson;
private String mobile;
/**
* 状态 1-启用 0-停用
*/
private Integer status;
/**
* 还款状态 1 有欠款 2 无欠款
*/
private Integer repaymentStatus;
/**
* 店铺id
*/
@JSONField(serialize = false)
private Long shopId;
public String getMobile() {
return CzgStrUtils.getStrOrNull(mobile);
}
public String getDebtor() {
return CzgStrUtils.getStrOrNull(debtor);
}
public String getId() {
return CzgStrUtils.getStrOrNull(id);
}
}

View File

@@ -3,6 +3,7 @@ package com.czg.order.service;
import com.czg.order.dto.CreditBuyerOrderDTO;
import com.czg.order.entity.CreditBuyerOrder;
import com.czg.order.entity.CreditPaymentRecord;
import com.czg.order.entity.OrderInfo;
import com.czg.order.param.CreditBuyerOrderQueryParam;
import com.czg.order.vo.CreditBuyerOrderSummaryVo;
import com.mybatisflex.core.paginate.Page;
@@ -46,17 +47,7 @@ public interface CreditBuyerOrderService extends IService<CreditBuyerOrder> {
* @param creditBuyerId 挂账人id
* @param orderId 订单id
*/
boolean save(String creditBuyerId, Long orderId);
/**
* 挂账人退款(整单退款)
*
* @param creditBuyerId 挂账人id
* @param orderId 订单id
* @return
*/
@Deprecated
boolean refund(String creditBuyerId, Long orderId);
boolean save(OrderInfo orderInfo, String creditBuyerId, Long orderId);
/**
@@ -67,6 +58,6 @@ public interface CreditBuyerOrderService extends IService<CreditBuyerOrder> {
* @param refundAmount 退款金额
* @return
*/
boolean partRefund(String creditBuyerId, Long orderId, BigDecimal refundAmount);
boolean partRefund(String creditBuyerId, Long orderId, String orderNo, BigDecimal refundAmount);
}

View File

@@ -1,6 +1,5 @@
package com.czg.order.service;
import com.czg.order.dto.CreditBuyerDTO;
import com.czg.order.entity.CreditBuyer;
import com.czg.order.param.CreditBuyerQueryParam;
import com.czg.order.param.CreditBuyerRepaymentParam;
@@ -15,13 +14,12 @@ import com.mybatisflex.core.service.IService;
* @since 1.0 2025-03-04
*/
public interface CreditBuyerService extends IService<CreditBuyer> {
Page<CreditBuyerDTO> getCreditBuyerPage(CreditBuyerQueryParam param);
Page<CreditBuyer> getCreditBuyerPage(CreditBuyerQueryParam param);
CreditBuyerDTO getCreditBuyerById(String id);
void addCreditBuyer(CreditBuyerDTO dto);
void addCreditBuyer(CreditBuyer dto);
void updateCreditBuyer(CreditBuyerDTO dto);
void updateCreditBuyer(CreditBuyer dto);
void deleteCreditBuyer(String id);

View File

@@ -25,14 +25,14 @@ public class CreditBuyerRepaymentVo implements Serializable {
* 还款金额
*/
private BigDecimal repaymentAmount;
/**
* 支付欠款
*/
private BigDecimal payAmount;
/**
* 转存金额
*/
private BigDecimal rechargeAmount;
// /**
// * 支付欠款
// */
// private BigDecimal payAmount;
// /**
// * 转存金额
// */
// private BigDecimal rechargeAmount;
/**
* 还款反馈消息
*/

View File

@@ -43,6 +43,11 @@ public class ProductDTO implements Serializable {
*/
@NotNull(message = "商品分类不能为空", groups = DefaultGroup.class)
private Long categoryId;
/**
* 商品分组
*/
private List<Long> proGroupIds;
/**
* 商品分类名称
*/
@@ -112,7 +117,7 @@ public class ProductDTO implements Serializable {
* 称重 价格/千克
*/
// @NotNull(message = "重量不能为空", groups = DefaultGroup.class)
private BigDecimal weight;
private String weight;
/**
* 是否允许临时改价
*/

View File

@@ -85,7 +85,7 @@ public class Product implements Serializable {
/**
* 称重 价格/千克
*/
private BigDecimal weight;
private String weight;
/**
* 是否允许临时改价
*/

View File

@@ -0,0 +1,44 @@
package com.czg.product.param;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
import java.util.List;
/**
* 商品批量操作
*
* @author ww
*/
@Data
public class ProductBatchParam implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
/**
* 商品id集合
*/
@NotNull(message = "商品id集合不能为空")
private List<Long> ids;
/**
* 商品操作
* category 修改分类
* isSale 上下架
* is_sold_stock 售罄
* isAutoSoldStock 自动售罄
*/
@NotBlank(message = "操作类型不能为空")
private String type;
/**
* 操作值
*/
@NotBlank(message = "操作值不能为空")
private String value;
/**
* 店铺id
*/
private Long shopId;
}

View File

@@ -110,7 +110,10 @@ public interface ProductService extends IService<Product> {
* @param param 商品报损入参
*/
void reportDamage(ProductReportDamageParam param);
/**
* 批量操作商品
*/
void batchOperate(ProductBatchParam param);
/**
* 商品统计
*

View File

@@ -64,6 +64,10 @@ public class ShopProductInfoVo implements Serializable {
* 是否售罄 1-是 0-否
*/
private Integer isSoldStock;
/**
* 是否自动售罄 1-是 0-否
*/
private Integer isAutoSoldStock;
/**
* 库存数量
*/

View File

@@ -1,19 +0,0 @@
package com.czg.service.account.mapper;
import com.czg.account.entity.MerchantRegister;
import com.czg.account.vo.MerchantRegisterVO;
import com.mybatisflex.core.BaseMapper;
import org.apache.ibatis.annotations.Param;
import java.util.List;
/**
* 激活码 映射层。
*
* @author Administrator
* @since 2025-02-11
*/
public interface MerchantRegisterMapper extends BaseMapper<MerchantRegister> {
List<MerchantRegisterVO> pageInfo(@Param("state") Integer state, @Param("startTime") String startTime, @Param("endTime") String endTime);
}

View File

@@ -0,0 +1,14 @@
package com.czg.service.account.mapper;
import com.czg.account.entity.ShopRegister;
import com.mybatisflex.core.BaseMapper;
/**
* 店铺签约 映射层。
*
* @author Administrator
* @since 2025-02-11
*/
public interface ShopRegisterMapper extends BaseMapper<ShopRegister> {
}

View File

@@ -1,47 +0,0 @@
package com.czg.service.account.service.impl;
import cn.hutool.core.util.IdUtil;
import com.czg.account.dto.PageDTO;
import com.czg.account.dto.register.MerchantRegisterDTO;
import com.czg.account.entity.MerchantRegister;
import com.czg.account.service.MerchantRegisterService;
import com.czg.service.account.mapper.MerchantRegisterMapper;
import com.czg.utils.PageUtil;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.mybatisflex.core.paginate.Page;
import com.mybatisflex.spring.service.impl.ServiceImpl;
import org.springframework.stereotype.Service;
import java.util.ArrayList;
/**
* 激活码 服务层实现。
*
* @author Administrator
* @since 2025-02-11
*/
@Service
public class MerchantRegisterServiceImpl extends ServiceImpl<MerchantRegisterMapper, MerchantRegister> implements MerchantRegisterService {
@Override
public Page<MerchantRegister> get(PageDTO pageDTO, Integer state, String startTime, String endTime) {
Page<Object> page = PageUtil.buildPage();
PageHelper.startPage(Math.toIntExact(page.getPageNumber()), Math.toIntExact(page.getPageSize()));
return PageUtil.convert(new PageInfo<>(mapper.pageInfo(state, startTime, endTime)));
}
@Override
public Boolean add(MerchantRegisterDTO merchantRegisterDTO) {
ArrayList<MerchantRegister> registers = new ArrayList<>();
for (int i = 0; i < merchantRegisterDTO.num(); i++) {
MerchantRegister tbMerchantRegister = new MerchantRegister();
tbMerchantRegister.setRegisterCode(IdUtil.simpleUUID());
tbMerchantRegister.setStatus(0);
tbMerchantRegister.setPeriodMonth(merchantRegisterDTO.periodMonth());
registers.add(tbMerchantRegister);
}
int i = mapper.insertBatchSelective(registers, 50);
return i > 0;
}
}

View File

@@ -21,12 +21,7 @@ import java.util.stream.Collectors;
* @since 2025-02-19
*/
@Service
public class ShopExtendServiceImpl extends ServiceImpl<ShopExtendMapper, ShopExtend> implements ShopExtendService{
private final static Map<String, String> KEY_MAP = Map.of(
"index_bg", "首页",
"my_bg", "我的页面背景图",
"member_bg", ""
);
public class ShopExtendServiceImpl extends ServiceImpl<ShopExtendMapper, ShopExtend> implements ShopExtendService {
@Override
public Boolean edit(Long shopId, ShopExtendDTO shopExtendDTO) {
@@ -36,8 +31,11 @@ public class ShopExtendServiceImpl extends ServiceImpl<ShopExtendMapper, ShopExt
}
BeanUtil.copyProperties(shopExtendDTO, shopExtend);
shopExtend.setAutoKey(null);
return update(shopExtend, new QueryWrapper().eq(ShopExtend::getShopId, shopId).eq(ShopExtend::getAutoKey, shopExtendDTO.getAutokey()));
if (shopExtendDTO.getValue() == null) {
shopExtend.setValue(null);
}
mapper.updateByQuery(shopExtend, false, new QueryWrapper().eq(ShopExtend::getShopId, shopId).eq(ShopExtend::getAutoKey, shopExtendDTO.getAutokey()));
return true;
}
@Override
@@ -53,7 +51,7 @@ public class ShopExtendServiceImpl extends ServiceImpl<ShopExtendMapper, ShopExt
public List<ShopExtend> checkAndInitialize(List<ShopExtend> shopExtendList, long shopId) {
List<ShopExtend> newRecords = new ArrayList<>();
List<String> requiredAutoKeys = Arrays.asList("index_bg", "my_bg", "member_bg", "shopinfo_bg","ticket_logo");
List<String> requiredAutoKeys = Arrays.asList("index_bg", "my_bg", "member_bg", "shopinfo_bg", "ticket_logo");
if (shopExtendList.isEmpty()) {
for (String key : requiredAutoKeys) {
@@ -61,7 +59,7 @@ public class ShopExtendServiceImpl extends ServiceImpl<ShopExtendMapper, ShopExt
newRecord.initAutoKey(key, shopId);
newRecords.add(newRecord);
}
mapper.insertBatchSelective(newRecords,50);
mapper.insertBatchSelective(newRecords, 50);
return newRecords;
} else {
for (ShopExtend shopExtend : shopExtendList) {
@@ -79,7 +77,7 @@ public class ShopExtendServiceImpl extends ServiceImpl<ShopExtendMapper, ShopExt
shopExtend.setName("商品列表");
break;
case "ticket_logo":
shopExtend.setName("小票logo");
shopExtend.setName("标签打印logo");
break;
}
}
@@ -98,7 +96,7 @@ public class ShopExtendServiceImpl extends ServiceImpl<ShopExtendMapper, ShopExt
}
if (!newRecords.isEmpty()) {
mapper.insertBatchSelective(newRecords,50);
mapper.insertBatchSelective(newRecords, 50);
}
shopExtendList.addAll(newRecords);

View File

@@ -63,7 +63,7 @@ public class ShopInfoServiceImpl extends ServiceImpl<ShopInfoMapper, ShopInfo> i
@Resource
private SysUserService sysUserService;
@Resource
private MerchantRegisterService merchantRegisterService;
private ShopRegisterService shopRegisterService;
@Resource
private ShopTableService shopTableService;
@Resource
@@ -147,22 +147,23 @@ public class ShopInfoServiceImpl extends ServiceImpl<ShopInfoMapper, ShopInfo> i
return page;
}
private void activateShop(ShopInfo shopInfo, String activateCode) {
MerchantRegister merchantRegister = merchantRegisterService.queryChain().eq(MerchantRegister::getRegisterCode, activateCode).one();
AssertUtil.isNull(merchantRegister, "激活码不存在");
if (merchantRegister.getStatus() == 1) {
throw new CzgException("激活码已使用");
}
// 续期
/**
* 签约店铺
* @param activateDuration 签约时长
* @param amount 续期费用
*/
private void activateShop(ShopInfo shopInfo, Integer activateDuration, BigDecimal amount) {
// 签约/续期
if (shopInfo.getExpireTime() != null && shopInfo.getExpireTime().isAfter(LocalDateTime.now())) {
shopInfo.setExpireTime(DateUtil.offsetMonth(DateUtil.date(shopInfo.getExpireTime()), merchantRegister.getPeriodMonth()).toLocalDateTime());
shopInfo.setExpireTime(DateUtil.offsetMonth(DateUtil.date(shopInfo.getExpireTime()), activateDuration).toLocalDateTime());
} else {
shopInfo.setExpireTime(DateUtil.offsetMonth(DateUtil.date(), merchantRegister.getPeriodMonth()).toLocalDateTime());
shopInfo.setExpireTime(DateUtil.offsetMonth(DateUtil.date(), activateDuration).toLocalDateTime());
}
merchantRegister.setStatus(1);
merchantRegister.setShopId(shopInfo.getId());
merchantRegisterService.updateById(merchantRegister);
ShopRegister register = new ShopRegister();
register.setShopId(shopInfo.getId());
register.setPeriodMonth(activateDuration);
register.setAmount(amount);
shopRegisterService.save(register);
}
@Override
@@ -207,10 +208,9 @@ public class ShopInfoServiceImpl extends ServiceImpl<ShopInfoMapper, ShopInfo> i
shopInfo.setProfiles("release");
}
save(shopInfo);
if (StrUtil.isNotBlank(shopInfoAddDTO.getActivateCode())) {
activateShop(shopInfo, shopInfoAddDTO.getActivateCode());
if (shopInfoAddDTO.getActivateDuration() != null) {
activateShop(shopInfo, shopInfoAddDTO.getActivateDuration(),shopInfoAddDTO.getActivateAmount());
}
// 增加支付方式
shopPayTypeService.addInfo(shopInfo.getId());
// 初始化积分霸王餐设置
@@ -264,6 +264,7 @@ public class ShopInfoServiceImpl extends ServiceImpl<ShopInfoMapper, ShopInfo> i
@Override
@CacheEvict(key = "#shopInfoEditDTO.id")
@Transactional(rollbackFor = Exception.class)
public Boolean edit(ShopInfoEditDTO shopInfoEditDTO) {
shopInfoEditDTO.setIsMemberPrice(null);
ShopInfo shopInfo;
@@ -298,8 +299,8 @@ public class ShopInfoServiceImpl extends ServiceImpl<ShopInfoMapper, ShopInfo> i
} else {
throw new CzgException("禁止连锁店/加盟店修改为单店");
}
if (shopInfoEditDTO.getActivateCode() != null) {
activateShop(shopInfo, shopInfoEditDTO.getActivateCode());
if (shopInfoEditDTO.getActivateDuration() != null) {
activateShop(shopInfo, shopInfoEditDTO.getActivateDuration(),shopInfoEditDTO.getActivateAmount());
}
BeanUtil.copyProperties(shopInfoEditDTO, shopInfo);
if (shopInfoEditDTO.getOperationPwd() != null) {

View File

@@ -11,6 +11,7 @@ import com.czg.account.entity.ShopPayType;
import com.czg.account.service.ShopPayTypeService;
import com.czg.service.account.mapper.ShopPayTypeMapper;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.ArrayList;
import java.util.List;
@@ -22,13 +23,13 @@ import java.util.List;
* @since 2025-02-26
*/
@Service
public class ShopPayTypeServiceImpl extends ServiceImpl<ShopPayTypeMapper, ShopPayType> implements ShopPayTypeService{
private final ArrayList<ShopPayType> payTypeArrayList = new ArrayList<>(){{
add(new ShopPayType().setPayType("cash").setPayName("现金").setIcon("https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/3/319005ffef734aa6a88d432459fa59d8.png"));
add(new ShopPayType().setPayType("bank").setPayName("银行卡").setIcon("https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/3/98e6199cc61a480b9c63617600b2f2fe.png"));
add(new ShopPayType().setPayType("scanCode").setPayName("扫码支付").setIcon("https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/3/3a344b46638547df81d5857a3c8cac66.png"));
add(new ShopPayType().setPayType("deposit").setPayName("储值卡").setIcon("https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/3/6f778df10ea74142a6cba310c2a19063.png"));
add(new ShopPayType().setPayType("virtual").setPayName("挂账支付").setIcon("https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/3/6f778df10ea74142a6cba310c2a19063.png").setIsShowShortcut(0));
public class ShopPayTypeServiceImpl extends ServiceImpl<ShopPayTypeMapper, ShopPayType> implements ShopPayTypeService {
private final ArrayList<ShopPayType> payTypeArrayList = new ArrayList<>() {{
add(new ShopPayType().setPayType("cash").setPayName("现金").setIcon("https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/3/319005ffef734aa6a88d432459fa59d8.png").setSorts(1));
add(new ShopPayType().setPayType("bank").setPayName("银行卡").setIcon("https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/3/98e6199cc61a480b9c63617600b2f2fe.png").setSorts(2));
add(new ShopPayType().setPayType("scanCode").setPayName("扫码支付").setIcon("https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/3/3a344b46638547df81d5857a3c8cac66.png").setSorts(3));
add(new ShopPayType().setPayType("deposit").setPayName("储值卡").setIcon("https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/3/6f778df10ea74142a6cba310c2a19063.png").setSorts(4));
add(new ShopPayType().setPayType("virtual").setPayName("挂账支付").setIcon("https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/3/6f778df10ea74142a6cba310c2a19063.png").setIsShowShortcut(0).setSorts(5));
}};
@Override
@@ -44,12 +45,56 @@ public class ShopPayTypeServiceImpl extends ServiceImpl<ShopPayTypeMapper, ShopP
});
}
@Override
@Transactional(rollbackFor = Exception.class)
public void updateSort(Long shopId, Integer payTypeId, Integer targetSort) {
// 1. 查询当前拖动的项
ShopPayType current = getById(payTypeId);
if (current == null) {
throw new RuntimeException("支付类型不存在");
}
Integer oldSort = current.getSorts();
// 如果位置没变,不处理
if (oldSort.equals(targetSort)) {
return;
}
// 2. 查询同店铺下所有支付类型(按排序升序)
QueryWrapper wrapper = QueryWrapper.create()
.eq(ShopPayType::getShopId, shopId)
.orderBy(ShopPayType::getSorts, true);
List<ShopPayType> list = list(wrapper);
// 3. 重新排序(核心算法)
for (int i = 0; i < list.size(); i++) {
ShopPayType item = list.get(i);
if (item.getId().equals(payTypeId)) {
// 当前拖动项,设置目标排序
item.setSorts(targetSort);
} else if (oldSort < targetSort) {
// 向下拖动:原排序 < 目标排序 → 中间项排序 -1
if (item.getSorts() > oldSort && item.getSorts() <= targetSort) {
item.setSorts(item.getSorts() - 1);
}
} else {
// 向上拖动:原排序 > 目标排序 → 中间项排序 +1
if (item.getSorts() < oldSort && item.getSorts() >= targetSort) {
item.setSorts(item.getSorts() + 1);
}
}
}
// 4. 批量更新排序
updateBatch(list);
}
@Override
public List<ShopPayType> getList(Long shopId) {
List<ShopPayType> list = list(new QueryWrapper().eq(ShopPayType::getShopId, StpKit.USER.getShopId()));
List<ShopPayType> list = list(new QueryWrapper().eq(ShopPayType::getShopId, StpKit.USER.getShopId()).orderBy(ShopPayType::getSorts, true));
if (list.isEmpty()) {
addInfo(shopId);
list = list(new QueryWrapper().eq(ShopPayType::getShopId, StpKit.USER.getShopId()));
list = list(new QueryWrapper().eq(ShopPayType::getShopId, StpKit.USER.getShopId()).orderBy(ShopPayType::getSorts, true));
}
return list;
}

View File

@@ -0,0 +1,18 @@
package com.czg.service.account.service.impl;
import com.czg.account.entity.ShopRegister;
import com.czg.account.service.ShopRegisterService;
import com.czg.service.account.mapper.ShopRegisterMapper;
import com.mybatisflex.spring.service.impl.ServiceImpl;
import org.springframework.stereotype.Service;
/**
* 店铺签约 服务层实现。
*
* @author Administrator
* @since 2025-02-11
*/
@Service
public class ShopRegisterServiceImpl extends ServiceImpl<ShopRegisterMapper, ShopRegister> implements ShopRegisterService {
}

View File

@@ -17,7 +17,6 @@ import com.mybatisflex.core.query.QueryWrapper;
import com.mybatisflex.spring.service.impl.ServiceImpl;
import jakarta.annotation.Resource;
import org.apache.dubbo.config.annotation.DubboService;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.ArrayList;
@@ -48,7 +47,7 @@ public class ShopStaffServiceImpl extends ServiceImpl<ShopStaffMapper, ShopStaff
@Override
@Transactional(rollbackFor = Exception.class)
public Boolean add(ShopStaffAddDTO shopStaffAddDTO) {
SysUser sysUser = sysUserService.addUser(shopStaffAddDTO.getName(), StpKit.USER.getLoginIdAsString() + "@" +shopStaffAddDTO.getAccountName(),
SysUser sysUser = sysUserService.addUser(shopStaffAddDTO.getName(), StpKit.USER.getLoginIdAsString() + "@" + shopStaffAddDTO.getAccountName(),
shopStaffAddDTO.getAccountPwd(), shopStaffAddDTO.getPhone(), shopStaffAddDTO.getRoleId());
ShopStaff shopStaff = BeanUtil.copyProperties(shopStaffAddDTO, ShopStaff.class);
shopStaff.setShopId(StpKit.USER.getLoginIdAsLong());
@@ -104,7 +103,7 @@ public class ShopStaffServiceImpl extends ServiceImpl<ShopStaffMapper, ShopStaff
BeanUtil.copyProperties(shopStaffEditDTO, shopStaff);
updateById(shopStaff);
if (shopStaffEditDTO.getShopPermissionIds() != null ) {
if (shopStaffEditDTO.getShopPermissionIds() != null) {
shopStaffPermissionService.updateChain().eq(ShopStaffPermission::getStaffId, shopStaff.getId())
.eq(ShopStaffPermission::getShopId, StpKit.USER.getShopId()).eq(ShopStaffPermission::getUserId, shopStaff.getId()).remove();
// 权限添加
@@ -152,7 +151,16 @@ public class ShopStaffServiceImpl extends ServiceImpl<ShopStaffMapper, ShopStaff
}
queryWrapper.eq(ShopStaff::getShopId, StpKit.USER.getLoginIdAsLong());
return page(PageUtil.buildPage(), queryWrapper);
Page<ShopStaff> page = page(PageUtil.buildPage(), queryWrapper);
for (ShopStaff record : page.getRecords()) {
SysUsersRoles sysUsersRoles = sysUsersRolesService.getOne(new QueryWrapper().eq(SysUsersRoles::getUserId, record.getId()));
if (sysUsersRoles != null) {
record.setRoleId(sysUsersRoles.getRoleId());
SysRole role = sysRoleService.getById(sysUsersRoles.getRoleId());
record.setRoleName(role == null ? "" : role.getName());
}
}
return page;
}
@Override

View File

@@ -124,7 +124,10 @@ public class SysMenuServiceImpl extends ServiceImpl<SysMenuMapper, SysMenu> impl
if (menuEditDTO.getApiInfo() != null && !menuEditDTO.getApiInfo().isEmpty()) {
menu.setApiInfo(JSONObject.toJSONString(menuEditDTO.getApiInfo()));
}
return updateById(menu);
if (menuEditDTO.getPid() == null) {
menu.setPid(null);
}
return updateById(menu, false);
}

View File

@@ -1,25 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.czg.service.account.mapper.MerchantRegisterMapper">
<select id="pageInfo" resultType="com.czg.account.vo.MerchantRegisterVO">
select a.*, b.shop_name, b.phone, b.register_type, b.expire_time
from tb_merchant_register as a
left join tb_shop_info as b on a.shop_id = b.id
<where>
<if test="state != null">
a.status=#{state}
</if>
<if test="startTime != null and startTime != ''">
a.create_time >= #{startTime}
</if>
<if test="endTime != null and endTime != ''">
a.create_time &lt;= #{endTime}
</if>
</where>
order by a.create_time desc
</select>
</mapper>

View File

@@ -0,0 +1,7 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.czg.service.account.mapper.ShopRegisterMapper">
</mapper>

View File

@@ -85,6 +85,15 @@ public class MkShopCouponRecordServiceImpl extends ServiceImpl<MkShopCouponRecor
Map.entry("购买会员赠券", "系统发送")
);
private static final Map<String, Long> RESULT_COUNT_MAP = Map.ofEntries(
Map.entry("用户领取", 0L),
Map.entry("分享获得", 0L),
Map.entry("群聊发放", 0L),
Map.entry("推广发放", 0L),
Map.entry("管理员赠送", 0L),
Map.entry("系统发送", 0L)
);
//"积分兑换", "用户领取"
@Override
@@ -161,12 +170,7 @@ public class MkShopCouponRecordServiceImpl extends ServiceImpl<MkShopCouponRecor
key -> tempMap.getOrDefault(key, 0L)
));
resultmap.put("categoryMap", categoryMap);
Map<String, Long> resultCountMap = new HashMap<>();
resultCountMap.put("用户领取", 0L);
resultCountMap.put("推广发放", 0L);
resultCountMap.put("管理员赠送", 0L);
resultCountMap.put("系统发送", 0L);
resultCountMap.put("群聊发放", 0L);
Map<String, Long> resultCountMap = new HashMap<>(RESULT_COUNT_MAP);
if (CollUtil.isNotEmpty(recordCountVO)) {
for (CouponRecordCountVO record : recordCountVO) {

View File

@@ -1,13 +1,9 @@
package com.czg.service.order.mapper;
import com.czg.order.dto.CreditBuyerDTO;
import com.czg.order.entity.CreditBuyer;
import com.czg.order.param.CreditBuyerQueryParam;
import com.mybatisflex.core.BaseMapper;
import org.apache.ibatis.annotations.Mapper;
import java.util.List;
/**
* 挂账人
*
@@ -17,6 +13,5 @@ import java.util.List;
@Mapper
public interface CreditBuyerMapper extends BaseMapper<CreditBuyer> {
List<CreditBuyerDTO> findCreditBuyerList(CreditBuyerQueryParam param);
}

View File

@@ -60,8 +60,8 @@ public class FeiPrinter extends PrinterHandler implements PrinterImpl {
}
@Override
protected void onlyKitchenPrint(OrderInfo orderInfo, OrderDetail orderDetail, PrintMachine machine) {
String buildDishPrintData = buildOnlyKitchenPrintData(getPickupNum(orderInfo), orderDetail);
protected void onlyKitchenPrint(Integer isCode, OrderInfo orderInfo, OrderDetail orderDetail, PrintMachine machine) {
String buildDishPrintData = buildOnlyKitchenPrintData(isCode, getPickupNum(orderInfo), orderDetail);
String voiceJson = "{\"bizType\":\"2\",\"content\":\"\"}";
if (1 == machine.getVolumeSwitch()) {
voiceJson = "{\"bizType\":\"2\",\"content\":\"新单来了,请注意查看\"}";

View File

@@ -155,7 +155,8 @@ public class PrintConfig implements ApplicationRunner {
machine.setVolumeSwitch(0);
}
isNotice = false;
FunUtils.safeRunVoid(() -> printer.onlyKitchenPrint(orderInfo, item, machine),
ShopInfo shopInfo = shopInfoService.getById(orderInfo.getShopId());
FunUtils.safeRunVoid(() -> printer.onlyKitchenPrint(shopInfo.getIsKitchenCode(), orderInfo, item, machine),
"订单id:{} ,后厨分单打印失败", orderInfo.getId());
// 保存已打印信息
redisService.set(RedisCst.kitchenOnly(orderInfo.getId(), machine.getId(), item.getId()), "", 20);

View File

@@ -337,7 +337,7 @@ public abstract class PrinterHandler {
/**
* 后厨 菜品打印
*/
protected abstract void onlyKitchenPrint(OrderInfo orderInfo, OrderDetail orderDetail, PrintMachine machine);
protected abstract void onlyKitchenPrint(Integer isCode, OrderInfo orderInfo, OrderDetail orderDetail, PrintMachine machine);
/**
* 后厨 退菜整单打印

View File

@@ -485,7 +485,7 @@ public interface PrinterImpl {
* @return 元数据
*/
default String buildOnlyKitchenPrintData(String pickupNumber, OrderDetail orderDetail) {
PrintLabel signLabelInfo = getSignLabelInfo();
PrintSignLabel signLabelInfo = getSignLabelInfo();
StringBuilder builder = new StringBuilder();
builder.append(formatLabel(pickupNumber, signLabelInfo.centerBold))
.append(signLabelInfo.br);
@@ -548,6 +548,10 @@ public interface PrinterImpl {
builder.append(formatLabel("【加急】", signLabelInfo.center, signLabelInfo.bold))
.append(signLabelInfo.br);
}
if (1 == isCode) {
builder.append(formatLabel("UP_ORDER_DETAIL:" + orderDetail.getId(), signLabelInfo.center, signLabelInfo.qr))
.append(signLabelInfo.br);
}
builder.append(signLabelInfo.br)
.append(signLabelInfo.out())
.append(signLabelInfo.cut);

View File

@@ -55,8 +55,8 @@ public class YxyPrinter extends PrinterHandler implements PrinterImpl {
@Override
protected void onlyKitchenPrint(OrderInfo orderInfo, OrderDetail orderDetail, PrintMachine machine) {
String buildDishPrintData = buildOnlyKitchenPrintData(getPickupNum(orderInfo), orderDetail);
protected void onlyKitchenPrint(Integer isCode, OrderInfo orderInfo, OrderDetail orderDetail, PrintMachine machine) {
String buildDishPrintData = buildOnlyKitchenPrintData(isCode, getPickupNum(orderInfo), orderDetail);
String voiceJson = "{\"bizType\":\"2\",\"content\":\"\"}";
if (1 == machine.getVolumeSwitch()) {
voiceJson = "{\"bizType\":\"2\",\"content\":\"新单来了,请注意查看\"}";
@@ -253,6 +253,7 @@ public class YxyPrinter extends PrinterHandler implements PrinterImpl {
/**
* 签名Token
*
* @param timestamp 时间戳13位
* @param requestId 请求ID自定义
* @return token信息

View File

@@ -7,7 +7,6 @@ import cn.hutool.core.util.NumberUtil;
import cn.hutool.core.util.StrUtil;
import com.czg.constants.SystemConstants;
import com.czg.exception.CzgException;
import com.czg.order.dto.CreditBuyerDTO;
import com.czg.order.dto.CreditBuyerOrderDTO;
import com.czg.order.entity.CreditBuyer;
import com.czg.order.entity.CreditBuyerOrder;
@@ -20,7 +19,6 @@ import com.czg.order.vo.CreditBuyerOrderSummaryVo;
import com.czg.service.order.mapper.CreditBuyerMapper;
import com.czg.service.order.mapper.CreditBuyerOrderMapper;
import com.czg.service.order.mapper.CreditPaymentRecordMapper;
import com.czg.service.market.mapper.OrderInfoMapper;
import com.czg.utils.PageUtil;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
@@ -53,8 +51,6 @@ public class CreditBuyerOrderServiceImpl extends ServiceImpl<CreditBuyerOrderMap
@Resource
@Lazy
private CreditBuyerService creditBuyerService;
@Resource
private OrderInfoMapper orderInfoMapper;
@Override
public Page<CreditBuyerOrderDTO> getCreditBuyerOrderPage(CreditBuyerOrderQueryParam param) {
@@ -103,6 +99,11 @@ public class CreditBuyerOrderServiceImpl extends ServiceImpl<CreditBuyerOrderMap
if (creditBuyer == null) {
throw new CzgException("挂账人不存在");
}
creditBuyer.setAccountBalance(NumberUtil.add(creditBuyer.getAccountBalance(), record.getRepaymentAmount()));
CreditBuyer upCreditBuyer = new CreditBuyer();
upCreditBuyer.setId(record.getCreditBuyerId());
upCreditBuyer.setAccountBalance(creditBuyer.getAccountBalance());
creditBuyerMapper.update(upCreditBuyer);
String repaymentMethod = creditBuyer.getRepaymentMethod();
if (!"order".equals(repaymentMethod)) {
throw new CzgException("该挂账人不支持按订单付款");
@@ -110,7 +111,8 @@ public class CreditBuyerOrderServiceImpl extends ServiceImpl<CreditBuyerOrderMap
CreditBuyerOrderQueryParam param = new CreditBuyerOrderQueryParam();
param.setCreditBuyerId(record.getCreditBuyerId());
param.setOrderId(Convert.toStr(record.getOrderId()));
CreditBuyerOrderDTO dto = super.mapper.getOne(param);
CreditBuyerOrder dto = getOne(query().eq(CreditBuyerOrder::getCreditBuyerId, record.getCreditBuyerId())
.eq(CreditBuyerOrder::getOrderId, record.getOrderId()));
if (dto == null) {
throw new CzgException("挂账订单不存在");
}
@@ -120,11 +122,12 @@ public class CreditBuyerOrderServiceImpl extends ServiceImpl<CreditBuyerOrderMap
if (NumberUtil.isLess(record.getRepaymentAmount(), BigDecimal.ZERO)) {
throw new CzgException("还款金额不能小于0");
}
if (NumberUtil.isGreater(record.getRepaymentAmount(), dto.getUnpaidAmount())) {
BigDecimal unpaidAmount = NumberUtil.sub(dto.getOrderAmount(), dto.getRefundAmount(), dto.getPaidAmount());
if (NumberUtil.isGreater(record.getRepaymentAmount(), unpaidAmount)) {
throw new CzgException("还款金额不能大于未支付金额");
}
CreditBuyerOrder entity = BeanUtil.copyProperties(dto, CreditBuyerOrder.class);
if (NumberUtil.equals(record.getRepaymentAmount(), dto.getUnpaidAmount())) {
if (NumberUtil.equals(record.getRepaymentAmount(), unpaidAmount)) {
entity.setStatus("paid");
} else {
entity.setStatus("partial");
@@ -140,11 +143,11 @@ public class CreditBuyerOrderServiceImpl extends ServiceImpl<CreditBuyerOrderMap
@Override
@Transactional(rollbackFor = Exception.class)
public boolean save(String creditBuyerId, Long orderId) {
public boolean save(OrderInfo orderInfo, String creditBuyerId, Long orderId) {
if (StrUtil.isBlank(creditBuyerId)) {
throw new CzgException("挂账人id不能为空");
}
CreditBuyerDTO creditBuyer = creditBuyerService.getCreditBuyerById(creditBuyerId);
CreditBuyer creditBuyer = creditBuyerService.getById(creditBuyerId);
if (creditBuyer == null) {
throw new CzgException("挂账人不存在");
}
@@ -156,84 +159,47 @@ public class CreditBuyerOrderServiceImpl extends ServiceImpl<CreditBuyerOrderMap
if (status != null && status == SystemConstants.OneZero.ZERO) {
throw new CzgException("挂账人已被停用");
}
OrderInfo orderInfo = orderInfoMapper.selectOneById(orderId);
if (orderInfo == null) {
throw new CzgException("订单不存在");
}
// 账户余额
BigDecimal accountBalance = creditBuyer.getAccountBalance();
// 如果有余额的话从余额里面扣除没有余额的话从信用额度里面扣除余额和信用额度都为0则不允许挂账余额+信用额度刚好够支付这笔订单的话需要同时减余额减信用额度
if (NumberUtil.isGreaterOrEqual(accountBalance, orderInfo.getOrderAmount())) {
// 减余额
creditBuyer.setAccountBalance(NumberUtil.sub(accountBalance, orderInfo.getOrderAmount()));
CreditBuyer dbRecord = BeanUtil.copyProperties(creditBuyer, CreditBuyer.class);
creditBuyerMapper.update(dbRecord);
// 记录还款记录
CreditPaymentRecord record = new CreditPaymentRecord();
record.setCreditBuyerId(creditBuyerId);
record.setOrderId(orderId);
record.setRepaymentAmount(orderInfo.getOrderAmount());
record.setPaymentMethod("余额支付");
record.setPaymentTime(LocalDateTime.now());
record.setRemark("挂账时余额充足,直接从余额扣除");
creditPaymentRecordMapper.insert(record);
CreditBuyerOrder entity = new CreditBuyerOrder();
entity.setCreditBuyerId(creditBuyerId);
entity.setOrderId(orderId);
boolean greater = NumberUtil.isGreater(orderInfo.getOrderAmount(), accountBalance);
if (greater) {
throw new CzgException(StrUtil.format("剩余可挂账金额{} ,不足{}元", accountBalance, orderInfo.getOrderAmount()));
}
// 减余额
creditBuyer.setAccountBalance(NumberUtil.sub(accountBalance, orderInfo.getOrderAmount()));
CreditBuyer upCreditBuyer = new CreditBuyer();
upCreditBuyer.setId(creditBuyerId);
upCreditBuyer.setAccountBalance(creditBuyer.getAccountBalance());
creditBuyerMapper.update(upCreditBuyer);
CreditBuyerOrder entity = new CreditBuyerOrder();
entity.setCreditBuyerId(creditBuyerId);
entity.setOrderId(orderId);
entity.setOrderAmount(orderInfo.getOrderAmount());
//减去订单金额 余额仍大于挂账额度 则全额付款
if (NumberUtil.isGreaterOrEqual(creditBuyer.getAccountBalance(), creditBuyer.getCreditAmount())) {
entity.setPaidAmount(orderInfo.getOrderAmount());
entity.setStatus("paid");
entity.setLastPaymentTime(LocalDateTime.now());
entity.setLastPaymentMethod(record.getPaymentMethod());
entity.setRemark(record.getRemark());
return super.save(entity);
} else {
if (NumberUtil.isGreater(accountBalance, creditBuyer.getCreditAmount())) {
entity.setStatus("partial");
entity.setPaidAmount(NumberUtil.sub(accountBalance, creditBuyer.getCreditAmount()));
} else {
entity.setStatus("unpaid");
entity.setPaidAmount(BigDecimal.ZERO);
}
}
CreditBuyerOrder entity = null;
if (NumberUtil.isGreater(accountBalance, BigDecimal.ZERO)) {
// 减余额
creditBuyer.setAccountBalance(BigDecimal.ZERO);
CreditBuyer dbRecord = BeanUtil.copyProperties(creditBuyer, CreditBuyer.class);
creditBuyerMapper.update(dbRecord);
// 记录还款记录
CreditPaymentRecord record = new CreditPaymentRecord();
record.setCreditBuyerId(creditBuyerId);
record.setOrderId(orderId);
record.setRepaymentAmount(accountBalance);
record.setPaymentMethod("余额支付");
record.setPaymentTime(LocalDateTime.now());
record.setRemark("挂账时余额不足,先扣除现有余额,其他的从挂账额度中扣除");
creditPaymentRecordMapper.insert(record);
entity = new CreditBuyerOrder();
entity.setCreditBuyerId(creditBuyerId);
entity.setOrderId(orderId);
entity.setPaidAmount(accountBalance);
entity.setStatus("partial");
entity.setLastPaymentTime(LocalDateTime.now());
entity.setLastPaymentMethod(record.getPaymentMethod());
entity.setRemark(record.getRemark());
//super.save(entity);
orderInfo.setPayAmount(NumberUtil.sub(orderInfo.getOrderAmount(), accountBalance));
}
// 剩余挂账额度
BigDecimal remainingAmount = creditBuyer.getRemainingAmount();
// 验证挂账金额是否大于剩余额度
boolean greater = NumberUtil.isGreater(orderInfo.getOrderAmount(), remainingAmount);
if (greater) {
throw new CzgException(StrUtil.format("{}:¥{}不能大于剩余挂账额度({})", "挂账金额", orderInfo.getOrderAmount(), remainingAmount));
}
if (entity == null) {
entity = new CreditBuyerOrder();
entity.setStatus("unpaid");
entity.setPaidAmount(BigDecimal.ZERO);
entity.setCreditBuyerId(creditBuyerId);
entity.setOrderId(orderId);
}
return super.saveOrUpdate(entity);
entity.setRefundAmount(BigDecimal.ZERO);
entity.setLastPaymentTime(LocalDateTime.now());
return save(entity);
}
@Override
@Deprecated
@Transactional(rollbackFor = Exception.class)
public boolean refund(String creditBuyerId, Long orderId) {
public boolean partRefund(String creditBuyerId, Long orderId, String orderNo, BigDecimal refundAmount) {
if (StrUtil.isBlank(creditBuyerId)) {
throw new CzgException("挂账人id不能为空");
}
@@ -241,66 +207,12 @@ public class CreditBuyerOrderServiceImpl extends ServiceImpl<CreditBuyerOrderMap
if (creditBuyer == null) {
throw new CzgException("挂账人不存在");
}
OrderInfo orderInfo = orderInfoMapper.selectOneById(orderId);
if (orderInfo == null) {
throw new CzgException("订单不存在");
}
CreditBuyerOrderQueryParam param = new CreditBuyerOrderQueryParam();
param.setCreditBuyerId(creditBuyerId);
param.setOrderId(Convert.toStr(orderId));
CreditBuyerOrderDTO dto = super.mapper.getOne(param);
if (dto == null) {
throw new CzgException("挂账订单不存在");
}
// 1.只挂账未还款的情况,直接删除挂账订单
if ("unpaid".equals(dto.getStatus())) {
super.mapper.deleteById(dto.getId());
return true;
}
// 2.部分还款/已还款,删除挂账订单+红冲还款记录,并把已还款金额退回余额或挂账额度
if ("partial".equals(dto.getStatus()) || "paid".equals(dto.getStatus())) {
// 已还款金额
BigDecimal paidAmount = dto.getPaidAmount();
// 已还款金额进行红冲
CreditPaymentRecord record = new CreditPaymentRecord();
record.setCreditBuyerId(creditBuyerId);
record.setOrderId(orderId);
record.setRepaymentAmount(NumberUtil.sub(BigDecimal.ZERO, paidAmount));
record.setPaymentMethod("挂账退款");
record.setPaymentTime(LocalDateTime.now());
record.setRemark(StrUtil.format("挂账订单:{}申请退款,已归还挂账额度或账户余额", orderInfo.getOrderNo()));
creditPaymentRecordMapper.insert(record);
// 删除挂账订单,恢复挂账额度
super.mapper.deleteById(dto.getId());
// 退回余额
creditBuyer.setAccountBalance(NumberUtil.add(creditBuyer.getAccountBalance(), paidAmount));
creditBuyerService.updateById(creditBuyer);
return true;
}
return false;
}
@Override
@Transactional(rollbackFor = Exception.class)
public boolean partRefund(String creditBuyerId, Long orderId, BigDecimal refundAmount) {
if (StrUtil.isBlank(creditBuyerId)) {
throw new CzgException("挂账人id不能为空");
}
CreditBuyerDTO creditBuyer = creditBuyerService.getCreditBuyerById(creditBuyerId);
if (creditBuyer == null) {
throw new CzgException("挂账人不存在");
}
OrderInfo orderInfo = orderInfoMapper.selectOneById(orderId);
if (orderInfo == null) {
throw new CzgException("订单不存在");
}
CreditBuyerOrderQueryParam param = new CreditBuyerOrderQueryParam();
param.setCreditBuyerId(creditBuyerId);
param.setOrderId(Convert.toStr(orderId));
CreditBuyerOrderDTO dto = mapper.getOne(param);
if (dto == null) {
CreditBuyerOrder creditBuyerOrder = getOne(query().eq(CreditBuyerOrder::getCreditBuyerId, creditBuyerId).eq(CreditBuyerOrder::getOrderId, orderId));
if (creditBuyerOrder == null) {
throw new CzgException("挂账订单不存在");
}
// 已还款金额进行红冲
@@ -310,10 +222,10 @@ public class CreditBuyerOrderServiceImpl extends ServiceImpl<CreditBuyerOrderMap
record.setRepaymentAmount(NumberUtil.sub(BigDecimal.ZERO, refundAmount));
record.setPaymentMethod("挂账退款");
record.setPaymentTime(LocalDateTime.now());
record.setRemark(StrUtil.format("挂账订单:{},申请退款¥{}元,已恢复挂账额度。", orderInfo.getOrderNo(), refundAmount));
record.setRemark(StrUtil.format("挂账订单:{},申请退款¥{}元,已恢复挂账额度。", orderNo, refundAmount));
creditPaymentRecordMapper.insert(record);
dto = mapper.getOne(param);
BigDecimal sub = NumberUtil.sub(refundAmount, dto.getUnpaidAmount());
//退款金额减去 待支付金额
BigDecimal sub = NumberUtil.sub(refundAmount, NumberUtil.sub(creditBuyerOrder.getOrderAmount(), creditBuyerOrder.getPaidAmount()));
if (NumberUtil.isGreater(sub, BigDecimal.ZERO)) {
CreditPaymentRecord flow = new CreditPaymentRecord();
flow.setCreditBuyerId(creditBuyerId);
@@ -321,16 +233,24 @@ public class CreditBuyerOrderServiceImpl extends ServiceImpl<CreditBuyerOrderMap
flow.setRepaymentAmount(sub);
flow.setPaymentMethod("转储余额");
flow.setPaymentTime(LocalDateTime.now());
flow.setRemark(StrUtil.format("挂账订单:{},申请退款¥{}元,由于此挂账订单已提前还款,溢出部分¥{}元将转储至账户余额。", orderInfo.getOrderNo(), refundAmount, sub));
flow.setRemark(StrUtil.format("挂账订单:{},申请退款¥{}元,由于此挂账订单已提前还款,溢出部分¥{}元将转储至账户余额。", orderNo, refundAmount, sub));
creditPaymentRecordMapper.insert(flow);
UpdateChain.of(CreditBuyerOrder.class)
.set(CreditBuyerOrder::getPaidAmount, NumberUtil.sub(dto.getPaidAmount(), sub))
.eq(CreditBuyerOrder::getId, dto.getId())
.set(CreditBuyerOrder::getPaidAmount, NumberUtil.sub(creditBuyerOrder.getPaidAmount(), sub))
.set(CreditBuyerOrder::getRefundAmount, NumberUtil.add(creditBuyerOrder.getRefundAmount(), sub))
.eq(CreditBuyerOrder::getId, creditBuyerOrder.getId())
.update();
// 退回余额
creditBuyer.setAccountBalance(NumberUtil.add(creditBuyer.getAccountBalance(), sub));
CreditBuyer entity = BeanUtil.copyProperties(dto, CreditBuyer.class);
CreditBuyer entity = new CreditBuyer();
entity.setId(creditBuyer.getId());
entity.setAccountBalance(creditBuyer.getAccountBalance());
creditBuyerService.updateById(entity);
} else {
UpdateChain.of(CreditBuyerOrder.class)
.set(CreditBuyerOrder::getRefundAmount, NumberUtil.add(creditBuyerOrder.getRefundAmount(), sub))
.eq(CreditBuyerOrder::getId, creditBuyerOrder.getId())
.update();
}
return true;
}

View File

@@ -10,7 +10,6 @@ import cn.hutool.core.util.NumberUtil;
import cn.hutool.core.util.StrUtil;
import com.czg.constants.SystemConstants;
import com.czg.exception.CzgException;
import com.czg.order.dto.CreditBuyerDTO;
import com.czg.order.dto.CreditBuyerOrderDTO;
import com.czg.order.entity.CreditBuyer;
import com.czg.order.entity.CreditBuyerOrder;
@@ -25,10 +24,8 @@ import com.czg.service.order.mapper.CreditBuyerMapper;
import com.czg.service.order.mapper.CreditBuyerOrderMapper;
import com.czg.service.order.mapper.CreditPaymentRecordMapper;
import com.czg.utils.PageUtil;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.github.pagehelper.PageParam;
import com.mybatisflex.core.paginate.Page;
import com.mybatisflex.core.query.QueryWrapper;
import com.mybatisflex.core.update.UpdateChain;
import com.mybatisflex.spring.service.impl.ServiceImpl;
import jakarta.annotation.Resource;
@@ -56,16 +53,26 @@ public class CreditBuyerServiceImpl extends ServiceImpl<CreditBuyerMapper, Credi
private CreditBuyerOrderMapper creditBuyerOrderMapper;
@Override
public Page<CreditBuyerDTO> getCreditBuyerPage(CreditBuyerQueryParam param) {
PageParam pageParam = PageUtil.buildPageHelp();
PageHelper.startPage(pageParam.getPageNum(), pageParam.getPageSize(), pageParam.getOrderBy());
public Page<CreditBuyer> getCreditBuyerPage(CreditBuyerQueryParam param) {
Long shopId = StpKit.USER.getShopId(0L);
param.setShopId(shopId);
PageInfo<CreditBuyerDTO> pageInfo = new PageInfo<>(super.mapper.findCreditBuyerList(param));
return PageUtil.convert(pageInfo);
QueryWrapper queryWrapper = query().eq(CreditBuyer::getShopId, shopId)
.like(CreditBuyer::getMobile, param.getMobile())
.like(CreditBuyer::getDebtor, param.getDebtor())
.eq(CreditBuyer::getStatus, param.getStatus())
.eq(CreditBuyer::getIsDel, SystemConstants.OneZero.ZERO);
if (param.getRepaymentStatus() != null) {
if (param.getRepaymentStatus() == 1) {
queryWrapper.where(CreditBuyer::getAccountBalance).gt(CreditBuyer::getCreditAmount);
} else {
queryWrapper.where(CreditBuyer::getAccountBalance).le(CreditBuyer::getCreditAmount);
}
}
return page(PageUtil.buildPage(), queryWrapper);
}
private void commonVerify(CreditBuyerDTO dto) {
private void commonVerify(CreditBuyer dto) {
try {
Assert.notNull(dto.getShopId(), "{}({})不能为空", "店铺id", "shopId");
Assert.notNull(dto.getStatus(), "{}({})不能为空", "状态", "status");
@@ -83,21 +90,9 @@ public class CreditBuyerServiceImpl extends ServiceImpl<CreditBuyerMapper, Credi
}
}
@Override
public CreditBuyerDTO getCreditBuyerById(String id) {
Long shopId = StpKit.USER.getShopId(0L);
CreditBuyerQueryParam param = new CreditBuyerQueryParam();
param.setId(id);
param.setShopId(shopId);
List<CreditBuyerDTO> list = super.mapper.findCreditBuyerList(param);
if (CollUtil.isEmpty(list)) {
return null;
}
return list.getFirst();
}
@Override
public void addCreditBuyer(CreditBuyerDTO dto) {
public void addCreditBuyer(CreditBuyer dto) {
Long shopId = StpKit.USER.getShopId(0L);
dto.setShopId(shopId);
commonVerify(dto);
@@ -109,13 +104,13 @@ public class CreditBuyerServiceImpl extends ServiceImpl<CreditBuyerMapper, Credi
if (!ArrayUtil.contains(new String[]{"total", "order"}, dto.getRepaymentMethod())) {
throw new CzgException(StrUtil.format("{}({})不合法", "还款方式", "repaymentMethod"));
}
dto.setAccountBalance(BigDecimal.ZERO);
dto.setAccountBalance(dto.getCreditAmount());
CreditBuyer entity = BeanUtil.copyProperties(dto, CreditBuyer.class);
super.save(entity);
}
@Override
public void updateCreditBuyer(CreditBuyerDTO dto) {
public void updateCreditBuyer(CreditBuyer dto) {
try {
Assert.notEmpty(dto.getId(), "{}不能为空", "id");
} catch (IllegalArgumentException e) {
@@ -128,18 +123,27 @@ public class CreditBuyerServiceImpl extends ServiceImpl<CreditBuyerMapper, Credi
if (entity == null) {
throw new CzgException("挂账人不存在");
}
CreditBuyerDTO record = getCreditBuyerById(dto.getId());
// 验证挂账额度是否小于已挂账金额
boolean less = NumberUtil.isLess(dto.getCreditAmount(), NumberUtil.nullToZero(record.getOwedAmount()));
if (less) {
throw new CzgException(StrUtil.format("{}({})不能小于已挂账金额({})", "挂账额度", "creditAmount", record.getOwedAmount()));
//余额减去挂账金额 100 60 挂账40 修改后 如果是 80
BigDecimal sub = NumberUtil.sub(dto.getCreditAmount(), entity.getCreditAmount());
//修改后的余额
BigDecimal balance = NumberUtil.add(entity.getAccountBalance(), sub);
if (NumberUtil.isLess(balance, BigDecimal.ZERO)) {
throw new CzgException("挂账额度不能小于已挂账金额");
}
BeanUtil.copyProperties(dto, entity, CopyOptions.create().setIgnoreNullValue(false).setIgnoreProperties("repaymentMethod", "accountBalance"));
super.updateById(entity);
entity.setAccountBalance(balance);
updateById(entity, false);
}
@Override
public void deleteCreditBuyer(String id) {
CreditBuyer entity = getById(id);
if (entity == null) {
throw new CzgException("挂账人不存在");
}
if (NumberUtil.isLess(entity.getAccountBalance(), entity.getCreditAmount())) {
throw new CzgException("删除失败,有未还款挂账金额。");
}
Long shopId = StpKit.USER.getShopId(0L);
UpdateChain.of(CreditBuyer.class)
.set(CreditBuyer::getIsDel, SystemConstants.OneZero.ONE)
@@ -160,7 +164,7 @@ public class CreditBuyerServiceImpl extends ServiceImpl<CreditBuyerMapper, Credi
} catch (IllegalArgumentException e) {
throw new CzgException(e.getMessage());
}
CreditBuyerDTO dto = getCreditBuyerById(param.getId());
CreditBuyer dto = getById(param.getId());
if (dto == null) {
throw new CzgException("挂账人不存在");
}
@@ -174,44 +178,28 @@ public class CreditBuyerServiceImpl extends ServiceImpl<CreditBuyerMapper, Credi
if (NumberUtil.isLess(repaymentAmount, BigDecimal.ZERO)) {
throw new CzgException("还款金额不能小于0");
}
BigDecimal initRepaymentAmount = NumberUtil.add(repaymentAmount, BigDecimal.ZERO);
// 已挂账金额
BigDecimal owedAmount = dto.getOwedAmount();
if (NumberUtil.equals(owedAmount, BigDecimal.ZERO)) {
dto.setAccountBalance(NumberUtil.add(dto.getAccountBalance(), repaymentAmount));
CreditBuyer entity = BeanUtil.copyProperties(dto, CreditBuyer.class);
super.updateById(entity);
CreditPaymentRecord record = new CreditPaymentRecord();
record.setCreditBuyerId(param.getId());
record.setRepaymentAmount(repaymentAmount);
record.setPaymentMethod(param.getPaymentMethod());
record.setPaymentTime(LocalDateTime.now());
record.setRemark(param.getRemark());
creditPaymentRecordMapper.insert(record);
CreditBuyer upEntity = new CreditBuyer();
upEntity.setId(param.getId());
upEntity.setAccountBalance(NumberUtil.add(dto.getAccountBalance(), repaymentAmount));
super.updateById(upEntity);
CreditPaymentRecord record2 = new CreditPaymentRecord();
record2.setCreditBuyerId(param.getId());
record2.setRepaymentAmount(repaymentAmount);
record2.setPaymentMethod(param.getPaymentMethod());
record2.setPaymentTime(LocalDateTime.now());
record2.setRemark(param.getRemark());
creditPaymentRecordMapper.insert(record2);
if (NumberUtil.isGreaterOrEqual(dto.getAccountBalance(), dto.getCreditAmount())) {
CreditBuyerRepaymentVo result = new CreditBuyerRepaymentVo();
result.setRepaymentCount(0);
result.setRepaymentAmount(repaymentAmount);
result.setRepaymentMsg(StrUtil.format("账单无需还款,{}元已转储至余额。", repaymentAmount));
result.setRepaymentMsg("账单无需还款,已转储至余额。");
return result;
}
// 转存余额
BigDecimal rechargeAmount = BigDecimal.ZERO;
if (NumberUtil.isGreater(repaymentAmount, owedAmount)) {
rechargeAmount = NumberUtil.sub(repaymentAmount, owedAmount);
dto.setAccountBalance(NumberUtil.add(dto.getAccountBalance(), rechargeAmount));
CreditBuyer entity = BeanUtil.copyProperties(dto, CreditBuyer.class);
super.updateById(entity);
CreditPaymentRecord record = new CreditPaymentRecord();
record.setCreditBuyerId(param.getId());
record.setRepaymentAmount(rechargeAmount);
record.setPaymentMethod(param.getPaymentMethod());
record.setPaymentTime(LocalDateTime.now());
record.setRemark(param.getRemark());
creditPaymentRecordMapper.insert(record);
}
// 校验完毕,可以批量还款
CreditBuyerOrderQueryParam where = new CreditBuyerOrderQueryParam();
where.setCreditBuyerId(param.getId());
where.setStatusList(List.of("unpaid", "partial"));
@@ -220,7 +208,7 @@ public class CreditBuyerServiceImpl extends ServiceImpl<CreditBuyerMapper, Credi
throw new CzgException("没有需要还款的订单");
}
int repaymentCount = 0;
List<CreditBuyerOrderDTO> orderList = list.stream().sorted(Comparator.comparing(CreditBuyerOrderDTO::getOrderId)).collect(Collectors.toList());
List<CreditBuyerOrderDTO> orderList = list.stream().sorted(Comparator.comparing(CreditBuyerOrderDTO::getOrderId)).toList();
for (CreditBuyerOrderDTO item : orderList) {
// 未付款金额
BigDecimal unpaidAmount = item.getUnpaidAmount();
@@ -271,12 +259,9 @@ public class CreditBuyerServiceImpl extends ServiceImpl<CreditBuyerMapper, Credi
}
}
CreditBuyerRepaymentVo result = new CreditBuyerRepaymentVo();
BigDecimal payAmount = NumberUtil.sub(initRepaymentAmount, repaymentAmount);
result.setRepaymentCount(repaymentCount);
result.setRepaymentAmount(initRepaymentAmount);
result.setPayAmount(payAmount);
result.setRechargeAmount(rechargeAmount);
result.setRepaymentMsg(StrUtil.format("共计还款{}笔,还款金额:{}元,支付欠款:{}元,转存余额:{}元,当前余额:{}元。", repaymentCount, initRepaymentAmount, payAmount, rechargeAmount, dto.getAccountBalance()));
result.setRepaymentMsg(StrUtil.format("共计还款{}笔,还款金额:{}元,当前余额:{}元。",
repaymentCount, NumberUtil.sub(param.getRepaymentAmount(), repaymentAmount), upEntity.getAccountBalance()));
return result;
}

View File

@@ -130,7 +130,7 @@ public class OrderPayServiceImpl implements OrderPayService {
orderInfoCustomService.upOrderInfo(orderInfo, orderInfo.getOrderAmount(),
LocalDateTime.now(), null, PayEnums.CREDIT_PAY);
//挂账后续逻辑
buyerOrderService.save(payParam.getCreditBuyerId().toString(), orderInfo.getId());
buyerOrderService.save(orderInfo, payParam.getCreditBuyerId().toString(), orderInfo.getId());
return CzgResult.success();
}
@@ -498,7 +498,7 @@ public class OrderPayServiceImpl implements OrderPayService {
shopUserService.updateMoney(shopUserMoneyEditDTO);
} else if (orderInfo.getPayType().equals(PayEnums.CREDIT_PAY.getValue())) {
AssertUtil.isNull(orderInfo.getCreditBuyerId(), "挂账单退款失败,未查询到挂账人");
buyerOrderService.partRefund(orderInfo.getCreditBuyerId().toString(), orderInfo.getId(), param.getRefundAmount());
buyerOrderService.partRefund(orderInfo.getCreditBuyerId().toString(), orderInfo.getId(), orderInfo.getOrderNo(), param.getRefundAmount());
} else if (!orderInfo.getPayType().equals(PayEnums.CASH_PAY.getValue())) {
//退款 param.getRefundAmount()
if (orderInfo.getPayOrderId() == null) {

View File

@@ -3,74 +3,4 @@
<mapper namespace="com.czg.service.order.mapper.CreditBuyerMapper">
<sql id="view_credit_buyer_order_count">
(SELECT
tb.credit_buyer_id AS credit_buyer_id,
tb.status AS status,
count( 0 ) AS count
FROM
<include refid="view_credit_buyer_order"/>
tb
GROUP BY tb.credit_buyer_id,tb.status)
</sql>
<sql id="view_credit_buyer_order">
(SELECT t1.id AS id,
t1.credit_buyer_id AS credit_buyer_id,
t1.order_id AS order_id,
t2.pay_amount - t2.refund_amount AS pay_amount,
t1.paid_amount AS paid_amount,
(t2.pay_amount - t2.refund_amount) - t1.paid_amount AS unpaid_amount,
t1.status AS status,
t2.create_time AS create_time,
t1.last_payment_time AS last_payment_time,
t1.last_payment_method AS last_payment_method,
t1.remark AS remark
FROM tb_credit_buyer_order t1
LEFT JOIN tb_order_info t2 ON t1.order_id = t2.id)
</sql>
<select id="findCreditBuyerList" resultType="com.czg.order.dto.CreditBuyerDTO">
select x1.*,
x2.shop_name,
ifnull(x3.owed_amount, 0 ) as owed_amount,
ifnull(x3.accumulate_amount,0) as accumulate_amount
from tb_credit_buyer x1
left join tb_shop_info x2 on x1.shop_id = x2.id
left join (select t.credit_buyer_id,ifnull(sum(t.unpaid_amount),0) as owed_amount,ifnull(sum(t.pay_amount),0) as
accumulate_amount from
<include refid="view_credit_buyer_order"/>
t
group by t.credit_buyer_id) x3 on x1.id = x3.credit_buyer_id
<where>
and x1.is_del = 0
and x1.shop_id = #{shopId}
<if test="id !=null and id != ''">
and x1.id = #{id}
</if>
<if test="responsiblePerson !=null and responsiblePerson != ''">
and x1.responsible_person like concat('%',#{responsiblePerson},'%')
</if>
<if test="status !=null">
and x1.status = #{status}
</if>
<if test="keywords !=null and keywords != ''">
and (x1.debtor like concat('%',#{keywords},'%') or x1.mobile like concat('%',#{keywords},'%'))
</if>
<if test="repaymentStatus !=null and repaymentStatus != ''">
<if test="repaymentStatus == 'unpaid'">
and 0 &lt; ifnull((select x.count from <include refid="view_credit_buyer_order_count"/> x where x.credit_buyer_id = x1.id and x.status = 'unpaid'),0)
and 0 = ifnull((select x.count from <include refid="view_credit_buyer_order_count"/> x where x.credit_buyer_id = x1.id and x.status = 'partial'),0)
</if>
<if test="repaymentStatus == 'partial'">
and 0 &lt; ifnull((select x.count from <include refid="view_credit_buyer_order_count"/> x where x.credit_buyer_id = x1.id and x.status = 'partial'),0)
</if>
<if test="repaymentStatus == 'paid'">
and 0 = ifnull((select sum(x.count) from <include refid="view_credit_buyer_order_count"/> x where x.credit_buyer_id = x1.id and x.status in ('unpaid','partial')),0)
</if>
</if>
</where>
order by x1.status desc,x1.id desc
</select>
</mapper>

View File

@@ -7,16 +7,15 @@
(SELECT t1.id AS id,
t1.credit_buyer_id AS credit_buyer_id,
t1.order_id AS order_id,
t2.pay_amount - t2.refund_amount AS pay_amount,
t1.order_amount AS pay_amount,
t1.paid_amount AS paid_amount,
(t2.pay_amount - t2.refund_amount) - t1.paid_amount AS unpaid_amount,
t1.order_amount - t1.refund_amount - t1.paid_amount AS unpaid_amount,
t1.status AS status,
t2.create_time AS create_time,
t1.create_time AS create_time,
t1.last_payment_time AS last_payment_time,
t1.last_payment_method AS last_payment_method,
t1.remark AS remark
FROM tb_credit_buyer_order t1
LEFT JOIN tb_order_info t2 ON t1.order_id = t2.id)
FROM tb_credit_buyer_order t1)
</sql>
<sql id="commonWhere">

View File

@@ -61,7 +61,20 @@ public class ProdGroupServiceImpl extends ServiceImpl<ProdGroupMapper, ProdGroup
@Override
public Page<ProdGroupDTO> getProdGroupPage(ProdGroupDTO param) {
QueryWrapper queryWrapper = buildQueryWrapper(param);
return super.pageAs(PageUtil.buildPage(), queryWrapper, ProdGroupDTO.class);
Page<ProdGroupDTO> page = pageAs(PageUtil.buildPage(), queryWrapper, ProdGroupDTO.class);
page.getRecords().forEach(group -> {
List<Long> productIdList = prodGroupRelationMapper.selectObjectListByQueryAs(query()
.select(ProdGroupRelation::getProductId).eq(ProdGroupRelation::getProdGroupId, group.getId()), Long.class);
if (CollUtil.isNotEmpty(productIdList)) {
List<ProductBriefDTO> productList = productMapper.selectListByQueryAs(query()
.select(Product::getId, Product::getCategoryId, Product::getName, Product::getCoverImg)
.in(Product::getId, productIdList), ProductBriefDTO.class);
group.setProductList(productList);
} else {
group.setProductList(new ArrayList<>());
}
});
return page;
}
@Override
@@ -77,7 +90,9 @@ public class ProdGroupServiceImpl extends ServiceImpl<ProdGroupMapper, ProdGroup
ProdGroupDTO dto = super.getOneAs(query().eq(ProdGroup::getId, id).eq(ProdGroup::getShopId, shopId), ProdGroupDTO.class);
List<Long> productIdList = prodGroupRelationMapper.selectObjectListByQueryAs(query().select(ProdGroupRelation::getProductId).eq(ProdGroupRelation::getProdGroupId, id), Long.class);
if (CollUtil.isNotEmpty(productIdList)) {
List<ProductBriefDTO> productList = productMapper.selectListByQueryAs(query().select(Product::getId, Product::getCategoryId, Product::getName, Product::getCoverImg).in(Product::getId, productIdList), ProductBriefDTO.class);
List<ProductBriefDTO> productList = productMapper.selectListByQueryAs(query()
.select(Product::getId, Product::getCategoryId, Product::getName, Product::getCoverImg)
.in(Product::getId, productIdList), ProductBriefDTO.class);
dto.setProductList(productList);
} else {
dto.setProductList(new ArrayList<>());
@@ -171,7 +186,7 @@ public class ProdGroupServiceImpl extends ServiceImpl<ProdGroupMapper, ProdGroup
@CacheEvict(value = {CacheConstant.USER_CLIENT_HOTS_PRODUCT, CacheConstant.USER_CLIENT_GROUPS_PRODUCT}, key = "#shopId", allEntries = true)
public void enableProdGroup(Long shopId, Long id) {
UpdateChain.of(ProdGroup.class)
.set(ProdGroup::getStatus,SystemConstants.OneZero.ONE)
.set(ProdGroup::getStatus, SystemConstants.OneZero.ONE)
.eq(ProdGroup::getId, id)
.eq(ProdGroup::getShopId, shopId)
.update();

View File

@@ -401,6 +401,19 @@ public class ProductServiceImpl extends ServiceImpl<ProductMapper, Product> impl
redisService.del(CacheConstant.USER_CLIENT_HOTS_PRODUCT + "::" + shopId);
}
/**
* 清除某个商品分类的缓存
*/
private void clearProductAllCache(Long shopId) {
//分类缓存
redisService.deleteKeysByPrefixSafe(ADMIN_CLIENT_PRODUCT_LIST + "::" + shopId);
//用户端分组缓存
redisService.del(CacheConstant.USER_CLIENT_GROUPS_PRODUCT + "::" + shopId);
//用户端热销缓存
redisService.del(CacheConstant.USER_CLIENT_HOTS_PRODUCT + "::" + shopId);
}
/**
* 计算是否在可售时间内
*
@@ -449,6 +462,8 @@ public class ProductServiceImpl extends ServiceImpl<ProductMapper, Product> impl
List<ProdConsRelationDTO> consList = prodConsRelationService.selectListByProdId(dto.getId());
dto.setConsList(consList);
dto.setRelatedRecommendJson(getRelateProductList(dto.getRelatedRecommend()));
dto.setProGroupIds(prodGroupRelationMapper.selectListByQueryAs(query().select(ProdGroupRelation::getProdGroupId)
.eq(ProdGroupRelation::getProductId, dto.getId()), Long.class));
return dto;
}
@@ -478,6 +493,18 @@ public class ProductServiceImpl extends ServiceImpl<ProductMapper, Product> impl
entity.setRelatedRecommend(dto.getRelatedRecommendStr());
super.save(entity);
dto.setId(entity.getId());
List<Long> groupIds = dto.getProGroupIds();
if (CollUtil.isNotEmpty(groupIds)) {
List<ProdGroupRelation> prodGroupRelations = new ArrayList<>();
for (Long groupId : groupIds) {
ProdGroupRelation prodGroupRelation = new ProdGroupRelation();
prodGroupRelation.setProductId(entity.getId());
prodGroupRelation.setProdGroupId(groupId);
prodGroupRelations.add(prodGroupRelation);
}
prodGroupRelationMapper.insertBatch(prodGroupRelations);
}
List<ProdSkuDTO> skuList = dto.getSkuList();
if (CollUtil.isNotEmpty(skuList)) {
List<ProdSku> prodSkuList = new ArrayList<>();
@@ -513,9 +540,7 @@ public class ProductServiceImpl extends ServiceImpl<ProductMapper, Product> impl
}
Product old = super.getById(dto.getId());
Product entity = BeanUtil.copyProperties(dto, Product.class);
if ("weight".equals(entity.getType()) && (entity.getWeight() == null || entity.getWeight().compareTo(BigDecimal.ZERO) <= 0)) {
throw new CzgException("称重商品重量必须大于0");
}
entity.setImages(JSON.toJSONString(dto.getImages(), JSONWriter.Feature.WriteMapNullValue));
entity.setGroupSnap("[]");
//套餐
@@ -556,6 +581,19 @@ public class ProductServiceImpl extends ServiceImpl<ProductMapper, Product> impl
List<Long> list = skuList.stream().map(ProdSkuDTO::getId).filter(Objects::nonNull).distinct().toList();
skuIdList.removeAll(list);
}
List<Long> groupIds = dto.getProGroupIds();
if (CollUtil.isNotEmpty(groupIds)) {
prodGroupRelationMapper.deleteByQuery(query().eq(ProdGroupRelation::getProductId, entity.getId()));
List<ProdGroupRelation> prodGroupRelations = new ArrayList<>();
for (Long groupId : groupIds) {
ProdGroupRelation prodGroupRelation = new ProdGroupRelation();
prodGroupRelation.setProductId(entity.getId());
prodGroupRelation.setProdGroupId(groupId);
prodGroupRelations.add(prodGroupRelation);
}
prodGroupRelationMapper.insertBatch(prodGroupRelations);
}
ProdConsBindDTO prodConsBindDTO = new ProdConsBindDTO();
prodConsBindDTO.setId(dto.getId());
prodConsBindDTO.setConsList(dto.getConsList());
@@ -717,6 +755,7 @@ public class ProductServiceImpl extends ServiceImpl<ProductMapper, Product> impl
Product update = new Product();
update.setIsAutoSoldStock(param.getIsAutoSoldStock());
update(update, query().eq(Product::getId, param.getId()).eq(Product::getShopId, shopId));
clearProductCache(entity.getCategoryId());
}
@@ -750,6 +789,32 @@ public class ProductServiceImpl extends ServiceImpl<ProductMapper, Product> impl
consStockByProduct(shopId, InOutTypeEnum.OUT, InOutItemEnum.DAMAGE_OUT, productStockList, null, "【商品报损,自动报损相关耗材】");
}
@Override
public void batchOperate(ProductBatchParam param) {
Product product = new Product();
//商品操作
//category 修改分类
//isSale 上下架
//is_sold_stock 售罄
//isAutoSoldStock 自动售罄
switch (param.getType()) {
case "category":
product.setCategoryId(Long.valueOf(param.getValue()));
break;
case "isSale":
product.setIsSale(Integer.valueOf(param.getValue()));
break;
case "is_sold_stock":
product.setIsSoldStock(Integer.valueOf(param.getValue()));
break;
case "isAutoSoldStock":
product.setIsAutoSoldStock(Integer.valueOf(param.getValue()));
break;
}
update(product, query().eq(Product::getShopId, param.getShopId()).in(Product::getId, param.getIds()));
clearProductAllCache(param.getShopId());
}
@Override
public ProductStatisticsVo getProductStatistics(ProductInfoParam param) {
ProductStatisticsVo data = productStockFlowMapper.getProductStatistics(param);