Commit 955b441b by Jony.L

商品展示 初步提交

parent fb777398
...@@ -144,6 +144,10 @@ ...@@ -144,6 +144,10 @@
<artifactId>spring-boot-starter-test</artifactId> <artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope> <scope>test</scope>
</dependency> </dependency>
<dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-redis</artifactId>
</dependency>
</dependencies> </dependencies>
</project> </project>
package com.luhu.computility.framework.common.core.redis;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.BoundSetOperations;
import org.springframework.data.redis.core.HashOperations;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.stereotype.Component;
import java.util.*;
import java.util.concurrent.TimeUnit;
/**
* @Author: jony
* @Date : 2025/7/30 16:52
* @VERSION v1.0
*/
@SuppressWarnings(value = { "unchecked", "rawtypes" })
@Component
public class RedisCache
{
@Autowired
public RedisTemplate redisTemplate;
/**
* 缓存基本的对象,Integer、String、实体类等
*
* @param key 缓存的键值
* @param value 缓存的值
*/
public <T> void setCacheObject(final String key, final T value)
{
redisTemplate.opsForValue().set(key, value);
}
/**
* 缓存基本的对象,Integer、String、实体类等
*
* @param key 缓存的键值
* @param value 缓存的值
* @param timeout 时间
* @param timeUnit 时间颗粒度
*/
public <T> void setCacheObject(final String key, final T value, final Integer timeout, final TimeUnit timeUnit)
{
redisTemplate.opsForValue().set(key, value, timeout, timeUnit);
}
/**
* 设置有效时间
*
* @param key Redis键
* @param timeout 超时时间
* @return true=设置成功;false=设置失败
*/
public boolean expire(final String key, final long timeout)
{
return expire(key, timeout, TimeUnit.SECONDS);
}
/**
* 设置有效时间
*
* @param key Redis键
* @param timeout 超时时间
* @param unit 时间单位
* @return true=设置成功;false=设置失败
*/
public boolean expire(final String key, final long timeout, final TimeUnit unit)
{
return redisTemplate.expire(key, timeout, unit);
}
/**
* 获取有效时间
*
* @param key Redis键
* @return 有效时间
*/
public long getExpire(final String key)
{
return redisTemplate.getExpire(key);
}
/**
* 判断 key是否存在
*
* @param key 键
* @return true 存在 false不存在
*/
public Boolean hasKey(String key)
{
return redisTemplate.hasKey(key);
}
/**
* 获得缓存的基本对象。
*
* @param key 缓存键值
* @return 缓存键值对应的数据
*/
public <T> T getCacheObject(final String key)
{
ValueOperations<String, T> operation = redisTemplate.opsForValue();
return operation.get(key);
}
/**
* 删除单个对象
*
* @param key
*/
public boolean deleteObject(final String key)
{
return redisTemplate.delete(key);
}
/**
* 删除集合对象
*
* @param collection 多个对象
* @return
*/
public boolean deleteObject(final Collection collection)
{
return redisTemplate.delete(collection) > 0;
}
/**
* 缓存List数据
*
* @param key 缓存的键值
* @param dataList 待缓存的List数据
* @return 缓存的对象
*/
public <T> long setCacheList(final String key, final List<T> dataList)
{
Long count = redisTemplate.opsForList().rightPushAll(key, dataList);
return count == null ? 0 : count;
}
/**
* 获得缓存的list对象
*
* @param key 缓存的键值
* @return 缓存键值对应的数据
*/
public <T> List<T> getCacheList(final String key)
{
return redisTemplate.opsForList().range(key, 0, -1);
}
/**
* 缓存Set
*
* @param key 缓存键值
* @param dataSet 缓存的数据
* @return 缓存数据的对象
*/
public <T> BoundSetOperations<String, T> setCacheSet(final String key, final Set<T> dataSet)
{
BoundSetOperations<String, T> setOperation = redisTemplate.boundSetOps(key);
Iterator<T> it = dataSet.iterator();
while (it.hasNext())
{
setOperation.add(it.next());
}
return setOperation;
}
/**
* 获得缓存的set
*
* @param key
* @return
*/
public <T> Set<T> getCacheSet(final String key)
{
return redisTemplate.opsForSet().members(key);
}
/**
* 缓存Map
*
* @param key
* @param dataMap
*/
public <T> void setCacheMap(final String key, final Map<String, T> dataMap)
{
if (dataMap != null) {
redisTemplate.opsForHash().putAll(key, dataMap);
}
}
/**
* 获得缓存的Map
*
* @param key
* @return
*/
public <T> Map<String, T> getCacheMap(final String key)
{
return redisTemplate.opsForHash().entries(key);
}
/**
* 往Hash中存入数据
*
* @param key Redis键
* @param hKey Hash键
* @param value 值
*/
public <T> void setCacheMapValue(final String key, final String hKey, final T value)
{
redisTemplate.opsForHash().put(key, hKey, value);
}
/**
* 获取Hash中的数据
*
* @param key Redis键
* @param hKey Hash键
* @return Hash中的对象
*/
public <T> T getCacheMapValue(final String key, final String hKey)
{
HashOperations<String, String, T> opsForHash = redisTemplate.opsForHash();
return opsForHash.get(key, hKey);
}
/**
* 获取多个Hash中的数据
*
* @param key Redis键
* @param hKeys Hash键集合
* @return Hash对象集合
*/
public <T> List<T> getMultiCacheMapValue(final String key, final Collection<Object> hKeys)
{
return redisTemplate.opsForHash().multiGet(key, hKeys);
}
/**
* 删除Hash中的某条数据
*
* @param key Redis键
* @param hKey Hash键
* @return 是否成功
*/
public boolean deleteCacheMapValue(final String key, final String hKey)
{
return redisTemplate.opsForHash().delete(key, hKey) > 0;
}
/**
* 获得缓存的基本对象列表
*
* @param pattern 字符串前缀
* @return 对象列表
*/
public Collection<String> keys(final String pattern)
{
return redisTemplate.keys(pattern);
}
}
...@@ -34,11 +34,11 @@ public class ComputilityWebAutoConfiguration implements WebMvcConfigurer { ...@@ -34,11 +34,11 @@ public class ComputilityWebAutoConfiguration implements WebMvcConfigurer {
@Resource @Resource
private WebProperties webProperties; private WebProperties webProperties;
/** // /**
* 应用名 // * 应用名
*/ // */
@Value("${spring.application.name}") // @Value("${spring.application.name}")
private String applicationName; // private String applicationName;
@Override @Override
public void configurePathMatch(PathMatchConfigurer configurer) { public void configurePathMatch(PathMatchConfigurer configurer) {
...@@ -58,16 +58,16 @@ public class ComputilityWebAutoConfiguration implements WebMvcConfigurer { ...@@ -58,16 +58,16 @@ public class ComputilityWebAutoConfiguration implements WebMvcConfigurer {
&& antPathMatcher.match(api.getController(), clazz.getPackage().getName())); // 仅仅匹配 controller 包 && antPathMatcher.match(api.getController(), clazz.getPackage().getName())); // 仅仅匹配 controller 包
} }
@Bean // @Bean
@SuppressWarnings("SpringJavaInjectionPointsAutowiringInspection") // @SuppressWarnings("SpringJavaInjectionPointsAutowiringInspection")
public GlobalExceptionHandler globalExceptionHandler(ApiErrorLogCommonApi apiErrorLogApi) { // public GlobalExceptionHandler globalExceptionHandler(ApiErrorLogCommonApi apiErrorLogApi) {
return new GlobalExceptionHandler(applicationName, apiErrorLogApi); // return new GlobalExceptionHandler(applicationName, apiErrorLogApi);
} // }
@Bean // @Bean
public GlobalResponseBodyHandler globalResponseBodyHandler() { // public GlobalResponseBodyHandler globalResponseBodyHandler() {
return new GlobalResponseBodyHandler(); // return new GlobalResponseBodyHandler();
} // }
@Bean @Bean
@SuppressWarnings("InstantiationOfUtilityClass") @SuppressWarnings("InstantiationOfUtilityClass")
......
...@@ -18,6 +18,7 @@ import com.luhu.computility.framework.common.biz.infra.logger.dto.ApiErrorLogCre ...@@ -18,6 +18,7 @@ import com.luhu.computility.framework.common.biz.infra.logger.dto.ApiErrorLogCre
import com.fasterxml.jackson.databind.exc.InvalidFormatException; import com.fasterxml.jackson.databind.exc.InvalidFormatException;
import lombok.AllArgsConstructor; import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j; import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.http.converter.HttpMessageNotReadableException; import org.springframework.http.converter.HttpMessageNotReadableException;
import org.springframework.security.access.AccessDeniedException; import org.springframework.security.access.AccessDeniedException;
import org.springframework.util.Assert; import org.springframework.util.Assert;
...@@ -49,7 +50,7 @@ import static com.luhu.computility.framework.common.exception.enums.GlobalErrorC ...@@ -49,7 +50,7 @@ import static com.luhu.computility.framework.common.exception.enums.GlobalErrorC
* @author 芋道源码 * @author 芋道源码
*/ */
@RestControllerAdvice @RestControllerAdvice
@AllArgsConstructor //@AllArgsConstructor
@Slf4j @Slf4j
public class GlobalExceptionHandler { public class GlobalExceptionHandler {
...@@ -60,15 +61,22 @@ public class GlobalExceptionHandler { ...@@ -60,15 +61,22 @@ public class GlobalExceptionHandler {
@SuppressWarnings("SpringJavaInjectionPointsAutowiringInspection") @SuppressWarnings("SpringJavaInjectionPointsAutowiringInspection")
private final String applicationName; private final String applicationName;
private final ApiErrorLogCommonApi apiErrorLogApi; private final ApiErrorLogCommonApi apiErrorLogApi;
public GlobalExceptionHandler(
@Value("${spring.application.name}") String applicationName, // 直接注入配置值
ApiErrorLogCommonApi apiErrorLogApi
) {
this.applicationName = applicationName;
this.apiErrorLogApi = apiErrorLogApi;
}
/** /**
* 处理所有异常,主要是提供给 Filter 使用 * 处理所有异常,主要是提供给 Filter 使用
* 因为 Filter 不走 SpringMVC 的流程,但是我们又需要兜底处理异常,所以这里提供一个全量的异常处理过程,保持逻辑统一。 * 因为 Filter 不走 SpringMVC 的流程,但是我们又需要兜底处理异常,所以这里提供一个全量的异常处理过程,保持逻辑统一。
* *
* @param request 请求 * @param request 请求
* @param ex 异常 * @param ex 异常
* @return 通用返回 * @return 通用返回
*/ */
public CommonResult<?> allExceptionHandler(HttpServletRequest request, Throwable ex) { public CommonResult<?> allExceptionHandler(HttpServletRequest request, Throwable ex) {
...@@ -110,7 +118,7 @@ public class GlobalExceptionHandler { ...@@ -110,7 +118,7 @@ public class GlobalExceptionHandler {
/** /**
* 处理 SpringMVC 请求参数缺失 * 处理 SpringMVC 请求参数缺失
* * <p>
* 例如说,接口上设置了 @RequestParam("xx") 参数,结果并未传递 xx 参数 * 例如说,接口上设置了 @RequestParam("xx") 参数,结果并未传递 xx 参数
*/ */
@ExceptionHandler(value = MissingServletRequestParameterException.class) @ExceptionHandler(value = MissingServletRequestParameterException.class)
...@@ -121,7 +129,7 @@ public class GlobalExceptionHandler { ...@@ -121,7 +129,7 @@ public class GlobalExceptionHandler {
/** /**
* 处理 SpringMVC 请求参数类型错误 * 处理 SpringMVC 请求参数类型错误
* * <p>
* 例如说,接口上设置了 @RequestParam("xx") 参数为 Integer,结果传递 xx 参数类型为 String * 例如说,接口上设置了 @RequestParam("xx") 参数为 Integer,结果传递 xx 参数类型为 String
*/ */
@ExceptionHandler(MethodArgumentTypeMismatchException.class) @ExceptionHandler(MethodArgumentTypeMismatchException.class)
...@@ -168,16 +176,16 @@ public class GlobalExceptionHandler { ...@@ -168,16 +176,16 @@ public class GlobalExceptionHandler {
/** /**
* 处理 SpringMVC 请求参数类型错误 * 处理 SpringMVC 请求参数类型错误
* * <p>
* 例如说,接口上设置了 @RequestBody实体中 xx 属性类型为 Integer,结果传递 xx 参数类型为 String * 例如说,接口上设置了 @RequestBody实体中 xx 属性类型为 Integer,结果传递 xx 参数类型为 String
*/ */
@ExceptionHandler(HttpMessageNotReadableException.class) @ExceptionHandler(HttpMessageNotReadableException.class)
public CommonResult<?> methodArgumentTypeInvalidFormatExceptionHandler(HttpMessageNotReadableException ex) { public CommonResult<?> methodArgumentTypeInvalidFormatExceptionHandler(HttpMessageNotReadableException ex) {
log.warn("[methodArgumentTypeInvalidFormatExceptionHandler]", ex); log.warn("[methodArgumentTypeInvalidFormatExceptionHandler]", ex);
if(ex.getCause() instanceof InvalidFormatException) { if (ex.getCause() instanceof InvalidFormatException) {
InvalidFormatException invalidFormatException = (InvalidFormatException) ex.getCause(); InvalidFormatException invalidFormatException = (InvalidFormatException) ex.getCause();
return CommonResult.error(BAD_REQUEST.getCode(), String.format("请求参数类型错误:%s", invalidFormatException.getValue())); return CommonResult.error(BAD_REQUEST.getCode(), String.format("请求参数类型错误:%s", invalidFormatException.getValue()));
}else { } else {
return defaultExceptionHandler(ServletUtils.getRequest(), ex); return defaultExceptionHandler(ServletUtils.getRequest(), ex);
} }
} }
...@@ -204,7 +212,7 @@ public class GlobalExceptionHandler { ...@@ -204,7 +212,7 @@ public class GlobalExceptionHandler {
/** /**
* 处理 SpringMVC 请求地址不存在 * 处理 SpringMVC 请求地址不存在
* * <p>
* 注意,它需要设置如下两个配置项: * 注意,它需要设置如下两个配置项:
* 1. spring.mvc.throw-exception-if-no-handler-found 为 true * 1. spring.mvc.throw-exception-if-no-handler-found 为 true
* 2. spring.mvc.static-path-pattern 为 /statics/** * 2. spring.mvc.static-path-pattern 为 /statics/**
...@@ -226,7 +234,7 @@ public class GlobalExceptionHandler { ...@@ -226,7 +234,7 @@ public class GlobalExceptionHandler {
/** /**
* 处理 SpringMVC 请求方法不正确 * 处理 SpringMVC 请求方法不正确
* * <p>
* 例如说,A 接口的方法为 GET 方式,结果请求方法为 POST 方式,导致不匹配 * 例如说,A 接口的方法为 GET 方式,结果请求方法为 POST 方式,导致不匹配
*/ */
@ExceptionHandler(HttpRequestMethodNotSupportedException.class) @ExceptionHandler(HttpRequestMethodNotSupportedException.class)
...@@ -237,7 +245,7 @@ public class GlobalExceptionHandler { ...@@ -237,7 +245,7 @@ public class GlobalExceptionHandler {
/** /**
* 处理 Spring Security 权限不足的异常 * 处理 Spring Security 权限不足的异常
* * <p>
* 来源是,使用 @PreAuthorize 注解,AOP 进行权限拦截 * 来源是,使用 @PreAuthorize 注解,AOP 进行权限拦截
*/ */
@ExceptionHandler(value = AccessDeniedException.class) @ExceptionHandler(value = AccessDeniedException.class)
...@@ -249,7 +257,7 @@ public class GlobalExceptionHandler { ...@@ -249,7 +257,7 @@ public class GlobalExceptionHandler {
/** /**
* 处理业务异常 ServiceException * 处理业务异常 ServiceException
* * <p>
* 例如说,商品库存不足,用户手机号已存在。 * 例如说,商品库存不足,用户手机号已存在。
*/ */
@ExceptionHandler(value = ServiceException.class) @ExceptionHandler(value = ServiceException.class)
...@@ -300,7 +308,7 @@ public class GlobalExceptionHandler { ...@@ -300,7 +308,7 @@ public class GlobalExceptionHandler {
// 执行插入 errorLog // 执行插入 errorLog
apiErrorLogApi.createApiErrorLogAsync(errorLog); apiErrorLogApi.createApiErrorLogAsync(errorLog);
} catch (Throwable th) { } catch (Throwable th) {
log.error("[createExceptionLog][url({}) log({}) 发生异常]", req.getRequestURI(), JsonUtils.toJsonString(errorLog), th); log.error("[createExceptionLog][url({}) log({}) 发生异常]", req.getRequestURI(), JsonUtils.toJsonString(errorLog), th);
} }
} }
......
...@@ -17,6 +17,13 @@ ...@@ -17,6 +17,13 @@
</description> </description>
<dependencies> <dependencies>
<dependency>
<groupId>com.luhu</groupId>
<artifactId>computility-module-product</artifactId>
<version>${revision}</version>
</dependency>
<dependency> <dependency>
<groupId>com.luhu</groupId> <groupId>com.luhu</groupId>
<artifactId>computility-module-system</artifactId> <artifactId>computility-module-system</artifactId>
......
package com.luhu.computility.module.biz.controller.app.index.vo;
import lombok.Data;
/**
* 计算资源首页 Response VO
*
* @Author: jony
* @Date : 2025/8/5 14:41
* @VERSION v1.0
*/
@Data
public class ComputeRespVO {
private String model;
private String cpu;
private String gpu;
private String memory;
private String storage;
private String term;
private String publicPrice;
}
package com.luhu.computility.module.biz.controller.client.dto;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.io.Serializable;
/**
* @Author: jony
* @Date : 2025/8/1 09:51
* @VERSION v1.0
*/
@Schema(description = "客户端 - 首页二级菜单接口返回 DTO")
@Data
public class MenuDTO implements Serializable {
private static final long serialVersionUID = 1L;
private String name;
private String value;
}
...@@ -61,6 +61,14 @@ public interface ProductSpuService { ...@@ -61,6 +61,14 @@ public interface ProductSpuService {
ProductSpuDO getSpu(Long id, boolean includeDeleted); ProductSpuDO getSpu(Long id, boolean includeDeleted);
/** /**
* 根据categoryId获得商品 SPU 列表
*
* @param categoryId
* @return
*/
List<ProductSpuDO> getSpuListByCategoryId(Long categoryId);
/**
* 获得商品 SPU 列表 * 获得商品 SPU 列表
* *
* @param ids 编号数组 * @param ids 编号数组
......
...@@ -198,6 +198,14 @@ public class ProductSpuServiceImpl implements ProductSpuService { ...@@ -198,6 +198,14 @@ public class ProductSpuServiceImpl implements ProductSpuService {
} }
@Override @Override
public List<ProductSpuDO> getSpuListByCategoryId(Long categoryId){
if (ObjectUtil.isEmpty(categoryId)) {
return Collections.emptyList();
}
return productSpuMapper.selectList("category_id", categoryId);
}
@Override
public List<ProductSpuDO> getSpuList(Collection<Long> ids) { public List<ProductSpuDO> getSpuList(Collection<Long> ids) {
if (CollUtil.isEmpty(ids)) { if (CollUtil.isEmpty(ids)) {
return Collections.emptyList(); return Collections.emptyList();
......
...@@ -113,6 +113,12 @@ ...@@ -113,6 +113,12 @@
<groupId>com.anji-plus</groupId> <groupId>com.anji-plus</groupId>
<artifactId>captcha-spring-boot-starter</artifactId> <!-- 验证码,一般用于登录使用 --> <artifactId>captcha-spring-boot-starter</artifactId> <!-- 验证码,一般用于登录使用 -->
</dependency> </dependency>
<dependency>
<groupId>com.alibaba.fastjson2</groupId>
<artifactId>fastjson2</artifactId>
<version>2.0.43</version>
<scope>compile</scope>
</dependency>
</dependencies> </dependencies>
......
package com.luhu.computility.module.system.service.dict; package com.luhu.computility.module.system.service.dict;
import cn.hutool.core.util.StrUtil; import cn.hutool.core.util.StrUtil;
import com.luhu.computility.framework.common.core.redis.RedisCache;
import com.luhu.computility.framework.common.pojo.PageResult; import com.luhu.computility.framework.common.pojo.PageResult;
import com.luhu.computility.framework.common.util.date.LocalDateTimeUtils; import com.luhu.computility.framework.common.util.date.LocalDateTimeUtils;
import com.luhu.computility.framework.common.util.object.BeanUtils; import com.luhu.computility.framework.common.util.object.BeanUtils;
import com.luhu.computility.framework.common.util.spring.SpringUtils;
import com.luhu.computility.framework.dict.core.DictFrameworkUtils;
import com.luhu.computility.module.system.controller.admin.dict.vo.type.DictTypePageReqVO; import com.luhu.computility.module.system.controller.admin.dict.vo.type.DictTypePageReqVO;
import com.luhu.computility.module.system.controller.admin.dict.vo.type.DictTypeSaveReqVO; import com.luhu.computility.module.system.controller.admin.dict.vo.type.DictTypeSaveReqVO;
import com.luhu.computility.module.system.dal.dataobject.dict.DictDataDO;
import com.luhu.computility.module.system.dal.dataobject.dict.DictTypeDO; import com.luhu.computility.module.system.dal.dataobject.dict.DictTypeDO;
import com.luhu.computility.module.system.dal.mysql.dict.DictDataMapper;
import com.luhu.computility.module.system.dal.mysql.dict.DictTypeMapper; import com.luhu.computility.module.system.dal.mysql.dict.DictTypeMapper;
import com.google.common.annotations.VisibleForTesting; import com.google.common.annotations.VisibleForTesting;
import com.luhu.computility.module.system.util.dict.DictUtils;
import org.springframework.stereotype.Service; import org.springframework.stereotype.Service;
import javax.annotation.PostConstruct;
import javax.annotation.Resource; import javax.annotation.Resource;
import java.time.LocalDateTime; import java.time.LocalDateTime;
import java.util.Comparator;
import java.util.List; import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
import static com.luhu.computility.framework.common.exception.util.ServiceExceptionUtil.exception; import static com.luhu.computility.framework.common.exception.util.ServiceExceptionUtil.exception;
import static com.luhu.computility.module.system.enums.ErrorCodeConstants.*; import static com.luhu.computility.module.system.enums.ErrorCodeConstants.*;
...@@ -32,6 +42,25 @@ public class DictTypeServiceImpl implements DictTypeService { ...@@ -32,6 +42,25 @@ public class DictTypeServiceImpl implements DictTypeService {
@Resource @Resource
private DictTypeMapper dictTypeMapper; private DictTypeMapper dictTypeMapper;
@Resource
private DictDataMapper dictDataMapper;
/**
* 项目启动时,初始化字典到缓存
*/
@PostConstruct
public void init(){
loadingDictCache();
}
private void loadingDictCache(){
List<DictDataDO> dictDataList = dictDataMapper.selectListByStatusAndDictType(0, null);
Map<String, List<DictDataDO>> dictDataMap = dictDataList.stream().collect(Collectors.groupingBy(DictDataDO::getDictType));
for(Map.Entry<String,List<DictDataDO>> entry : dictDataMap.entrySet()){
DictUtils.setDictCache(entry.getKey(), entry.getValue().stream().sorted(Comparator.comparing(DictDataDO::getSort)).collect(Collectors.toList()));
}
}
@Override @Override
public PageResult<DictTypeDO> getDictTypePage(DictTypePageReqVO pageReqVO) { public PageResult<DictTypeDO> getDictTypePage(DictTypePageReqVO pageReqVO) {
return dictTypeMapper.selectPage(pageReqVO); return dictTypeMapper.selectPage(pageReqVO);
......
package com.luhu.computility.module.system.util.dict;
import cn.hutool.core.util.ObjectUtil;
import com.alibaba.fastjson2.JSONArray;
import com.luhu.computility.framework.common.core.redis.RedisCache;
import com.luhu.computility.framework.common.util.spring.SpringUtils;
import com.luhu.computility.module.system.dal.dataobject.dict.DictDataDO;
import org.apache.commons.lang3.StringUtils;
import java.util.ArrayList;
import java.util.List;
/**
* 字典工具类
*
* @Author: jony
* @Date : 2025/7/31 09:55
* @VERSION v1.0
*/
public class DictUtils {
/**
* 分隔符
*/
public static final String SEPARATOR = ",";
/**
* 设置字典缓存
*
* @param key 参数键
* @param dictDatas 字典数据列表
*/
public static void setDictCache(String key, List<DictDataDO> dictDatas) {
SpringUtils.getBean(RedisCache.class).setCacheObject(getCacheKey(key), dictDatas);
}
/**
* 获取字典缓存
*
* @param key 参数键
* @return dictDatas 字典数据列表
*/
public static List<DictDataDO> getDictCache(String key) {
// JSONArray arrayCache = SpringUtils.getBean(RedisCache.class).getCacheObject(getCacheKey(key));
// if (ObjectUtil.isNotNull(arrayCache)) {
// return arrayCache.toJavaList(DictDataDO.class);
// }
// return null;
Object cacheObj = SpringUtils.getBean(RedisCache.class).getCacheObject(getCacheKey(key));
if (cacheObj == null) {
return null;
}
List<DictDataDO> dictList;
if (cacheObj instanceof JSONArray) {
// 新数据:JSONArray 直接转 List
dictList = ((JSONArray) cacheObj).toJavaList(DictDataDO.class);
} else if (cacheObj instanceof ArrayList) {
dictList = (List<DictDataDO>) cacheObj;
} else {
// 其他未知类型,返回空列表(避免报错)
dictList = new ArrayList<>();
}
return dictList;
}
/**
* 根据字典类型和字典值获取字典标签
*
* @param dictType 字典类型
* @param dictValue 字典值
* @return 字典标签
*/
public static String getDictLabel(String dictType, String dictValue) {
return getDictLabel(dictType, dictValue, SEPARATOR);
}
/**
* 根据字典类型和字典标签获取字典值
*
* @param dictType 字典类型
* @param dictLabel 字典标签
* @return 字典值
*/
public static String getDictValue(String dictType, String dictLabel) {
return getDictValue(dictType, dictLabel, SEPARATOR);
}
/**
* 根据字典类型和字典值获取字典标签
*
* @param dictType 字典类型
* @param dictValue 字典值
* @param separator 分隔符
* @return 字典标签
*/
public static String getDictLabel(String dictType, String dictValue, String separator) {
StringBuilder propertyString = new StringBuilder();
List<DictDataDO> datas = getDictCache(dictType);
if (ObjectUtil.isNotNull(datas)) {
if (StringUtils.containsAny(separator, dictValue)) {
for (DictDataDO dict : datas) {
for (String value : dictValue.split(separator)) {
if (value.equals(dict.getValue())) {
propertyString.append(dict.getLabel()).append(separator);
break;
}
}
}
} else {
for (DictDataDO dict : datas) {
if (dictValue.equals(dict.getValue())) {
return dict.getLabel();
}
}
}
}
return StringUtils.stripEnd(propertyString.toString(), separator);
}
/**
* 根据字典类型和字典标签获取字典值
*
* @param dictType 字典类型
* @param dictLabel 字典标签
* @param separator 分隔符
* @return 字典值
*/
public static String getDictValue(String dictType, String dictLabel, String separator) {
StringBuilder propertyString = new StringBuilder();
List<DictDataDO> datas = getDictCache(dictType);
if (StringUtils.containsAny(separator, dictLabel) && ObjectUtil.isNotEmpty(datas)) {
for (DictDataDO dict : datas) {
for (String label : dictLabel.split(separator)) {
if (label.equals(dict.getLabel())) {
propertyString.append(dict.getValue()).append(separator);
break;
}
}
}
} else {
for (DictDataDO dict : datas) {
if (dictLabel.equals(dict.getLabel())) {
return dict.getValue();
}
}
}
return StringUtils.stripEnd(propertyString.toString(), separator);
}
/**
* 删除指定字典缓存
*
* @param key 字典键
*/
public static void removeDictCache(String key) {
SpringUtils.getBean(RedisCache.class).deleteObject(getCacheKey(key));
}
/**
* 清空字典缓存
*/
public static void clearDictCache() {
// Collection<String> keys = SpringUtils.getBean(RedisCache.class).keys(CacheConstants.SYS_DICT_KEY + "*");
SpringUtils.getBean(RedisCache.class).deleteObject("*");
}
/**
* 设置cache key
*
* @param configKey 参数键
* @return 缓存键key
*/
public static String getCacheKey(String configKey) {
// return CacheConstants.SYS_DICT_KEY + configKey;
return "sys_dict:" + configKey;
}
}
package com.luhu.computility.server; package com.luhu.computility.server;
import com.luhu.computility.module.system.dal.mysql.dict.DictDataMapper;
import org.springframework.boot.SpringApplication; import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;
/** /**
* 项目的启动类 * 项目的启动类
...@@ -13,7 +15,7 @@ import org.springframework.boot.autoconfigure.SpringBootApplication; ...@@ -13,7 +15,7 @@ import org.springframework.boot.autoconfigure.SpringBootApplication;
* @author 芋道源码 * @author 芋道源码
*/ */
@SuppressWarnings("SpringComponentScan") // 忽略 IDEA 无法识别 ${computility.info.base-package} @SuppressWarnings("SpringComponentScan") // 忽略 IDEA 无法识别 ${computility.info.base-package}
@SpringBootApplication(scanBasePackages = {"${computility.info.base-package}.server", "${computility.info.base-package}.module"}) @SpringBootApplication(scanBasePackages = {"${computility.info.base-package}.server", "${computility.info.base-package}.module", "${computility.info.base-package}.framework"})
public class ComputilityServerApplication { public class ComputilityServerApplication {
public static void main(String[] args) { public static void main(String[] args) {
...@@ -21,7 +23,7 @@ public class ComputilityServerApplication { ...@@ -21,7 +23,7 @@ public class ComputilityServerApplication {
// 如果你碰到启动的问题,请认真阅读 https://doc.iocoder.cn/quick-start/ 文章 // 如果你碰到启动的问题,请认真阅读 https://doc.iocoder.cn/quick-start/ 文章
// 如果你碰到启动的问题,请认真阅读 https://doc.iocoder.cn/quick-start/ 文章 // 如果你碰到启动的问题,请认真阅读 https://doc.iocoder.cn/quick-start/ 文章
SpringApplication.run(ComputilityServerApplication.class, args); ConfigurableApplicationContext run = SpringApplication.run(ComputilityServerApplication.class, args);
// new SpringApplicationBuilder(ComputilityServerApplication.class) // new SpringApplicationBuilder(ComputilityServerApplication.class)
// .applicationStartup(new BufferingApplicationStartup(20480)) // .applicationStartup(new BufferingApplicationStartup(20480))
// .run(args); // .run(args);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or sign in to comment