diff --git a/yudao-framework/yudao-spring-boot-starter-excel/pom.xml b/yudao-framework/yudao-spring-boot-starter-excel/pom.xml
index 0413986a64..0316c62e50 100644
--- a/yudao-framework/yudao-spring-boot-starter-excel/pom.xml
+++ b/yudao-framework/yudao-spring-boot-starter-excel/pom.xml
@@ -46,6 +46,12 @@
easyexcel
+
+ jakarta.validation
+ jakarta.validation-api
+ provided
+
+
com.google.guava
guava
diff --git a/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/core/DictFrameworkUtils.java b/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/core/DictFrameworkUtils.java
index 9fc67bfe7f..2a2350f02b 100644
--- a/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/core/DictFrameworkUtils.java
+++ b/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/core/DictFrameworkUtils.java
@@ -76,4 +76,9 @@ public class DictFrameworkUtils {
return dictData!= null ? dictData.getValue(): null;
}
+ @SneakyThrows
+ public static List getDictDataValueList(String dictType) {
+ List dictDatas = GET_DICT_DATA_CACHE.get(dictType);
+ return convertList(dictDatas, DictDataRespDTO::getValue);
+ }
}
diff --git a/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/validation/InDict.java b/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/validation/InDict.java
new file mode 100644
index 0000000000..dab0af782f
--- /dev/null
+++ b/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/validation/InDict.java
@@ -0,0 +1,38 @@
+package cn.iocoder.yudao.framework.dict.validation;
+
+import jakarta.validation.Constraint;
+import jakarta.validation.Payload;
+
+import java.lang.annotation.Documented;
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+@Target({
+ ElementType.METHOD,
+ ElementType.FIELD,
+ ElementType.ANNOTATION_TYPE,
+ ElementType.CONSTRUCTOR,
+ ElementType.PARAMETER,
+ ElementType.TYPE_USE
+})
+@Retention(RetentionPolicy.RUNTIME)
+@Documented
+@Constraint(
+ validatedBy = {InDictValidator.class, InDictCollectionValidator.class}
+)
+public @interface InDict {
+
+ /**
+ * 数据字典type
+ */
+ String type();
+
+ String message() default "必须在指定范围 {value}";
+
+ Class>[] groups() default {};
+
+ Class extends Payload>[] payload() default {};
+
+}
diff --git a/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/validation/InDictCollectionValidator.java b/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/validation/InDictCollectionValidator.java
new file mode 100644
index 0000000000..ab036171e2
--- /dev/null
+++ b/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/validation/InDictCollectionValidator.java
@@ -0,0 +1,40 @@
+package cn.iocoder.yudao.framework.dict.validation;
+
+import cn.iocoder.yudao.framework.common.util.string.StrUtils;
+import cn.iocoder.yudao.framework.dict.core.DictFrameworkUtils;
+import jakarta.validation.ConstraintValidator;
+import jakarta.validation.ConstraintValidatorContext;
+
+import java.util.Collection;
+import java.util.List;
+
+public class InDictCollectionValidator implements ConstraintValidator> {
+
+ private String dictType;
+
+ @Override
+ public void initialize(InDict annotation) {
+ this.dictType = annotation.type();
+ }
+
+ @Override
+ public boolean isValid(Collection> list, ConstraintValidatorContext context) {
+ if (list == null) {
+ return true;
+ }
+ List dbValues = DictFrameworkUtils.getDictDataValueList(dictType);
+ boolean match = list.stream().allMatch(v -> dbValues.stream()
+ .anyMatch(dbValue -> dbValue.equalsIgnoreCase(v.toString())));
+ if (match) {
+ return true;
+ }
+ // 校验不通过,自定义提示语句
+ context.disableDefaultConstraintViolation(); // 禁用默认的 message 的值
+ context.buildConstraintViolationWithTemplate(
+ context.getDefaultConstraintMessageTemplate().replaceAll("\\{value}",dbValues.toString())
+ ).addConstraintViolation(); // 重新添加错误提示语句
+ return false;
+ }
+
+}
+
diff --git a/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/validation/InDictValidator.java b/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/validation/InDictValidator.java
new file mode 100644
index 0000000000..05f50cb839
--- /dev/null
+++ b/yudao-framework/yudao-spring-boot-starter-excel/src/main/java/cn/iocoder/yudao/framework/dict/validation/InDictValidator.java
@@ -0,0 +1,40 @@
+package cn.iocoder.yudao.framework.dict.validation;
+
+import cn.iocoder.yudao.framework.common.util.string.StrUtils;
+import cn.iocoder.yudao.framework.dict.core.DictFrameworkUtils;
+import jakarta.validation.ConstraintValidator;
+import jakarta.validation.ConstraintValidatorContext;
+
+import java.util.List;
+
+public class InDictValidator implements ConstraintValidator {
+
+ private String dictType;
+
+ @Override
+ public void initialize(InDict annotation) {
+ this.dictType = annotation.type();
+ }
+
+ @Override
+ public boolean isValid(Object value, ConstraintValidatorContext context) {
+ // 为空时,默认不校验,即认为通过
+ if (value == null) {
+ return true;
+ }
+ // 校验通过
+ final List values = DictFrameworkUtils.getDictDataValueList(dictType);
+ boolean match = values.stream().anyMatch(v -> v.equalsIgnoreCase(value.toString()));
+ if (match) {
+ return true;
+ }
+ // 校验不通过,自定义提示语句
+ context.disableDefaultConstraintViolation(); // 禁用默认的 message 的值
+ context.buildConstraintViolationWithTemplate(
+ context.getDefaultConstraintMessageTemplate().replaceAll("\\{value}", values.toString())
+ ).addConstraintViolation(); // 重新添加错误提示语句
+ return false;
+ }
+
+}
+