Java 在spring引导服务中自定义constraintvalidator之前,Json消息解析失败

Java 在spring引导服务中自定义constraintvalidator之前,Json消息解析失败,java,json,spring-boot,Java,Json,Spring Boot,我需要验证使用enum作为字段的DTOBean,以实现与这里提供的一些解决方案相同的效果,但是json反序列化甚至在到达我的自定义验证器之前就失败了 其他开发人员在此提供的解决方案 import javax.validation.Constraint; import javax.validation.Payload; import java.lang.annotation.*; @Documented @Constraint(validatedBy = {EnumValueValidator.

我需要验证使用enum作为字段的DTOBean,以实现与这里提供的一些解决方案相同的效果,但是json反序列化甚至在到达我的自定义验证器之前就失败了

其他开发人员在此提供的解决方案

import javax.validation.Constraint;
import javax.validation.Payload;
import java.lang.annotation.*;

@Documented
@Constraint(validatedBy = {EnumValueValidator.class})
@Retention(RetentionPolicy.RUNTIME)
@Target({
  ElementType.ANNOTATION_TYPE,
  ElementType.CONSTRUCTOR,
  ElementType.FIELD,
  ElementType.METHOD,
  ElementType.PARAMETER
})
public @interface EnumValue {
  public abstract String message() default "{validation.enum.message}";

  public abstract Class<?>[] groups() default {};

  public abstract Class<? extends Payload>[] payload() default {};

  public abstract Class<? extends java.lang.Enum<?>> enumClass();
}



import javax.validation.ConstraintValidator;
import javax.validation.ConstraintValidatorContext;

public class EnumValueValidator implements ConstraintValidator<EnumValue, Object> {
  private Object[] enumValues;

  @Override
  public void initialize(final EnumValue annotation) {
    enumValues = annotation.enumClass().getEnumConstants();
  }

  @Override
  public boolean isValid(final Object value, final ConstraintValidatorContext context) {
    if (null != value) {
      String contextValue = value.toString();

      for (Object enumValue : enumValues) {
        if (enumValue.toString().equals(contextValue)) {
          return true;
        }
      }
    }

    return false;
  }
}


我在控制器中的请求方法如下:

 @PostMapping("/widget/type")
  public ResponseEntity<String> addWidgetTypes(
      @Validated @RequestBody ValidatorList<WidgetTypeAddOrUpdateDTO> widgetTypeDTOs) {
    widgetTypeService.add(widgetTypeDTOs.getValidatedList());
    return ResponseEntity.created(URI.create("/dashboard/admin/widget/type")).build();
  }

要应用验证,需要使用@Valid注释。您必须缺少@Valid,这就是您的验证无法工作的原因。 有关更多信息:

稍后还有一个问题。 在DTO WidgetTypeAdd或UpdatedTo中,枚举值持有者变量的类型为IsActive,它是一个枚举。当spring从JSON填充/反序列化DTO时,如果枚举值无效,它将抛出异常,因此需要将其更改为字符串类型。一旦您将其更改为字符串,则字符串可以包含任何文本,但您的验证将被绑定,并且如果存在无效值,将产生验证错误。 有关更多信息:

请发布控制器和导致错误的请求,尽管我知道您提供的解决方案,但我真的厌倦了以枚举的方式处理此问题,因此我将按照您的说法进行处理。谢谢
 @PostMapping("/widget/type")
  public ResponseEntity<String> addWidgetTypes(
      @Validated @RequestBody ValidatorList<WidgetTypeAddOrUpdateDTO> widgetTypeDTOs) {
    widgetTypeService.add(widgetTypeDTOs.getValidatedList());
    return ResponseEntity.created(URI.create("/dashboard/admin/widget/type")).build();
  }
Resolved [org.springframework.http.converter.HttpMessageNotReadableException: JSON parse error: Cannot deserialize value of type `com.xyz.dashboardservice.common.IsActive` from String "xyz": value not one of declared Enum instance names: [NOT_ACTIVE, ACTIVE]