You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

自定义ConstraintValidator校验器无法Autowired注入Bean如何解决

问题根因

默认Hibernate Validator创建自定义校验器实例时,会直接通过反射调用类的无参构造方法完成实例化,不会经过Spring IOC容器。你当前的自定义校验器仅定义了带MyService参数的构造方法,未提供无参构造,因此直接抛出java.lang.NoSuchMethodException: <init>()异常;同时由于实例不是Spring容器管理的,@Autowired注解也不会生效。

解决方案(推荐)

通过配置将校验器的实例化交给Spring容器管理,即可支持依赖注入。

步骤1:配置Spring校验工厂

新增校验配置类,指定使用Spring提供的校验器工厂来创建校验器实例:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.validation.beanvalidation.LocalValidatorFactoryBean;
import org.springframework.validation.beanvalidation.SpringConstraintValidatorFactory;
import javax.validation.Validator;

@Configuration
public class ValidationConfig {

    @Bean
    public Validator validator(SpringConstraintValidatorFactory springConstraintValidatorFactory) {
        LocalValidatorFactoryBean factoryBean = new LocalValidatorFactoryBean();
        factoryBean.setConstraintValidatorFactory(springConstraintValidatorFactory);
        return factoryBean;
    }
}

步骤2:修改自定义校验器

给校验器添加@Component注解,将其纳入Spring容器管理,直接使用构造注入即可:

@Slf4j
@Component
@RequiredArgsConstructor // 无需手动写构造方法,Lombok会生成带final属性的构造函数
public class MyValidator implements ConstraintValidator<ValidMapper, String> {
    
    private final MyService myService;
  
    @Override
    public boolean isValid(String valueToValid, ConstraintValidatorContext context) {  
        // 直接使用注入的myService执行业务逻辑即可
        return true;
    }
}
备选方案(手动获取Bean)

如果不想调整全局校验配置,可以通过Spring上下文工具类手动获取业务Bean:

步骤1:实现Spring上下文工具类

import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import org.springframework.stereotype.Component;

@Component
public class SpringContextHolder implements ApplicationContextAware {
    private static ApplicationContext CONTEXT;

    @Override
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
        CONTEXT = applicationContext;
    }

    public static <T> T getBean(Class<T> beanClass) {
        return CONTEXT.getBean(beanClass);
    }
}

步骤2:在校验器初始化时获取Bean

@Slf4j
public class MyValidator implements ConstraintValidator<ValidMapper, String> {
    
    private MyService myService;
  
    @Override
    public void initialize(ValidMapper constraintAnnotation) {
        // 初始化时手动从Spring上下文获取业务Bean
        this.myService = SpringContextHolder.getBean(MyService.class);
    }

    @Override
    public boolean isValid(String valueToValid, ConstraintValidatorContext context) {  
        // 正常使用myService即可
        return true;
    }
}

内容的提问来源于stack exchange,提问作者Rio85

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.25 00:45:05