Merge branch 'test' into prod

# Conflicts:
#	cash-api/account-server/src/main/java/com/czg/controller/admin/AuthorizationController.java
#	cash-api/order-server/src/main/java/com/czg/controller/DistributionPayController.java
#	cash-service/order-service/src/main/java/com/czg/service/order/service/impl/OrderInfoCustomServiceImpl.java
#	cash-service/order-service/src/main/java/com/czg/service/order/service/impl/PayServiceImpl.java
This commit is contained in:
2026-01-17 09:52:55 +08:00
209 changed files with 11116 additions and 3013 deletions

View File

@@ -0,0 +1,14 @@
package com.czg.service.account.mapper;
import com.mybatisflex.core.BaseMapper;
import com.czg.account.entity.QuickMenu;
/**
* 悬浮窗配置 映射层。
*
* @author ww
* @since 2025-12-29
*/
public interface QuickMenuMapper extends BaseMapper<QuickMenu> {
}

View File

@@ -1,14 +0,0 @@
package com.czg.service.account.mapper;
import com.czg.account.entity.ShopMerchant;
import com.mybatisflex.core.BaseMapper;
/**
* 第三方商户进件 映射层。
*
* @author Administrator
* @since 2025-02-11
*/
public interface ShopMerchantMapper extends BaseMapper<ShopMerchant> {
}

View File

@@ -14,9 +14,9 @@ import com.czg.config.RedisCst;
import com.czg.constants.ParamCodeCst;
import com.czg.exception.CzgException;
import com.czg.resp.CzgResult;
import com.czg.service.RedisService;
import com.czg.service.account.mapper.CallQueueMapper;
import com.czg.service.account.mapper.CallTableMapper;
import com.czg.service.account.util.FunUtil;
import com.czg.service.account.util.WechatMiniMsgUtil;
import com.czg.system.dto.SysParamsDTO;
import com.czg.system.service.SysParamsService;
@@ -29,6 +29,7 @@ import jakarta.annotation.Resource;
import org.apache.dubbo.config.annotation.DubboReference;
import org.apache.dubbo.config.annotation.DubboService;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import java.io.ByteArrayOutputStream;
import java.util.*;
@@ -41,7 +42,7 @@ import java.util.stream.Collectors;
* @author zs
* @since 2025-02-21
*/
@DubboService
@Service
public class CallTableServiceImpl extends ServiceImpl<CallTableMapper, CallTable> implements CallTableService {
@DubboReference
private SysParamsService sysParamsService;
@@ -51,10 +52,10 @@ public class CallTableServiceImpl extends ServiceImpl<CallTableMapper, CallTable
@Resource
private ShopUserService shopUserService;
@Resource
private FunUtil funUtil;
@Resource
private StringRedisTemplate stringRedisTemplate;
@Resource
private RedisService redisService;
@Resource
private ShopInfoService shopInfoService;
@Resource
private CallConfigService callConfigService;
@@ -228,13 +229,13 @@ public class CallTableServiceImpl extends ServiceImpl<CallTableMapper, CallTable
}
private String getCallNumber(Long shopId, CallTable callTable) {
return funUtil.runFunAndCheckKey(() -> {
return redisService.runFunAndCheckKey(() -> {
String callNumKey = RedisCst.getTableCallNumKey(shopId, callTable.getId());
String value = stringRedisTemplate.opsForValue().get(callNumKey);
AtomicReference<String> newVal = new AtomicReference<>("");
// 初始化
if (StrUtil.isBlank(value)) {
Boolean setFlag = FunUtil.runFunAndRetry(() -> stringRedisTemplate.opsForValue().setIfAbsent(callNumKey, callTable.getStart().toString()), flag -> !flag,
Boolean setFlag = RedisService.runFunAndRetry(() -> stringRedisTemplate.opsForValue().setIfAbsent(callNumKey, callTable.getStart().toString()), flag -> !flag,
_ -> newVal.set(stringRedisTemplate.opsForValue().get(callNumKey)));
if (setFlag) {

View File

@@ -0,0 +1,18 @@
package com.czg.service.account.service.impl;
import com.mybatisflex.spring.service.impl.ServiceImpl;
import com.czg.account.entity.QuickMenu;
import com.czg.account.service.QuickMenuService;
import com.czg.service.account.mapper.QuickMenuMapper;
import org.springframework.stereotype.Service;
/**
* 悬浮窗配置 服务层实现。
*
* @author ww
* @since 2025-12-29
*/
@Service
public class QuickMenuServiceImpl extends ServiceImpl<QuickMenuMapper, QuickMenu> implements QuickMenuService{
}

View File

@@ -1,55 +0,0 @@
package com.czg.service.account.service.impl;
import cn.hutool.core.bean.BeanUtil;
import com.czg.account.dto.merchant.ShopMerchantEditDTO;
import com.czg.account.entity.ShopMerchant;
import com.czg.account.service.ShopMerchantService;
import com.czg.sa.StpKit;
import com.czg.service.account.mapper.ShopMerchantMapper;
import com.czg.utils.AssertUtil;
import com.mybatisflex.spring.service.impl.ServiceImpl;
import org.apache.dubbo.config.annotation.DubboService;
import org.springframework.cache.annotation.CacheConfig;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.Cacheable;
import java.io.Serializable;
/**
* 第三方商户进件 服务层实现。
*
* @author Administrator
* @since 2025-02-11
*/
@CacheConfig(cacheNames = "shop:merchant")
@DubboService
public class ShopMerchantServiceImpl extends ServiceImpl<ShopMerchantMapper, ShopMerchant> implements ShopMerchantService {
@Override
public ShopMerchant detail(Integer shopId) {
ShopMerchant one = queryChain().eq(ShopMerchant::getShopId, shopId).one();
return one == null ? new ShopMerchant() : one;
}
@CacheEvict(key = "#shopMerchantEditDTO.shopId")
@Override
public Boolean edit(ShopMerchantEditDTO shopMerchantEditDTO) {
ShopMerchant shopMerchant = queryChain().eq(ShopMerchant::getShopId, shopMerchantEditDTO.getShopId()).one();
if (shopMerchant == null) {
shopMerchant = new ShopMerchant();
shopMerchant.setShopId(shopMerchantEditDTO.getShopId());
BeanUtil.copyProperties(shopMerchantEditDTO, shopMerchant);
return save(shopMerchant);
}
BeanUtil.copyProperties(shopMerchantEditDTO, shopMerchant);
return updateById(shopMerchant);
}
@Cacheable(key = "#id")
@Override
public ShopMerchant getById(Serializable id) {
ShopMerchant shopMerchant = getMapper().selectOneById(id);
AssertUtil.isNull(shopMerchant, "暂未开通支付");
return shopMerchant;
}
}

View File

@@ -22,7 +22,6 @@ import com.czg.market.vo.InviteUserVO;
import com.czg.market.vo.MemberConfigVO;
import com.czg.order.entity.OrderInfo;
import com.czg.service.account.mapper.ShopUserMapper;
import com.czg.service.account.util.FunUtil;
import com.czg.utils.FunUtils;
import com.czg.utils.PageUtil;
import com.github.pagehelper.PageHelper;

View File

@@ -1,100 +0,0 @@
package com.czg.service.account.util;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.script.DefaultRedisScript;
import org.springframework.stereotype.Component;
import java.util.Collections;
import java.util.concurrent.TimeUnit;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Supplier;
/**
* @author Administrator
*/
@Slf4j
@Component
public class FunUtil {
@Resource
private RedisTemplate<String, Object> redisTemplate;
public static int retryCount = 5;
/**
* 执行任务并保证锁唯一
* @param supplier 业务逻辑
* @param lockKey Redis锁的Key
* @return 业务逻辑返回值
*/
public <T> T runFunAndCheckKey(Supplier<T> supplier, String lockKey) {
String lockValue = String.valueOf(System.nanoTime() + Thread.currentThread().threadId());
try {
// 尝试获取锁,超时时间 5 秒,防止死锁
boolean lock = Boolean.TRUE.equals(redisTemplate.opsForValue().setIfAbsent(lockKey, lockValue, 5, TimeUnit.SECONDS));
int count = 0;
// 初始等待 10ms
int retryDelay = 10;
while (!lock) {
// 最多重试 10 次,大约 10 秒
if (count++ > 50) {
throw new RuntimeException("系统繁忙, 稍后再试");
}
Thread.sleep(retryDelay);
// 指数退避,最大等待 200ms
retryDelay = Math.min(retryDelay * 2, 200);
lock = Boolean.TRUE.equals(redisTemplate.opsForValue().setIfAbsent(lockKey, lockValue, 5, TimeUnit.SECONDS));
}
// 执行任务
return supplier.get();
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
throw new RuntimeException("线程被中断", e);
} catch (Exception e) {
log.error("执行出错:{}", e.getMessage(), e);
throw e;
} finally {
// 释放锁(使用 Lua 脚本确保原子性)
unlock(lockKey, lockValue);
}
}
/**
* 使用 Lua 脚本确保释放锁的原子性
* @param lockKey 锁的 Key
* @param lockValue 当前线程的锁值
*/
private void unlock(String lockKey, String lockValue) {
String luaScript =
"if redis.call('get', KEYS[1]) == ARGV[1] then " +
"return redis.call('del', KEYS[1]) " +
"else return 0 end";
redisTemplate.execute(new DefaultRedisScript<>(luaScript, Long.class),
Collections.singletonList(lockKey), lockValue);
}
public static <T, R> R runFunAndRetry(
Supplier<R> function,
Function<R, Boolean> check, Consumer<R> errFun) {
log.info("工具类开始执行函数");
R result = function.get();
boolean flag = check.apply(result);
log.info("执行结果: {}", result);
while (flag && retryCount-- > 0) {
log.info("执行函数失败, 剩余尝试次数{}", retryCount);
result = function.get();
log.info("执行结果: {}", result);
flag = check.apply(result);
}
if (flag) {
errFun.accept(result);
}
return result;
}
}

View File

@@ -2,6 +2,6 @@
<!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.ShopMerchantMapper">
<mapper namespace="com.czg.service.account.mapper.QuickMenuMapper">
</mapper>