gpt4 book ai didi

Spring Boot - Hibernate 自定义约束不注入(inject)服务

转载 作者:行者123 更新时间:2023-12-02 09:56:50 26 4
gpt4 key购买 nike

我会尝试忽略其他细节并使其简短:

@Entity
public class User
@UniqueEmail
@Column(unique = true)
private String email;
}

@Component
public class UniqueEmailValidatior implements ConstraintValidator<UniqueEmail,String>, InitializingBean {

@Autowired private UserService userService;

@Override
public void initialize(UniqueEmail constraintAnnotation) {

}

@Override
public boolean isValid(String value, ConstraintValidatorContext context) {
if(userService == null) throw new IllegalStateException();
if(value == null) return false;
return !userService.isEmailExisted(value);
}

}

当在 Spring 中进行验证时(Spring MVC @Valid 或使用 @Autowire 注入(inject) Validator),这将起作用,一切都会没事的。但是一旦我使用 Spring Data JPA 保存实体:

User save = userRepository.save(newUser);

Hibernate 将尝试实例化一个新的 UniqueEmailValidatior 而不注入(inject) UserService bean。那么我怎样才能让 Hibernate 使用我的 UniqueEmailValidatior 组件而不实例化一个新组件。我可以使用 spring.jpa.properties.javax.persistence.validation.mode=none 禁用休眠验证,但我希望还有另一种方法

更新:这是我的 UserService:

   @Autowired private Validator validator;
@Transactional
public SimpleUserDTO newUser(UserRegisterDTO user) {
validator.validate(user);
System.out.println("This passes");
User newUser = new User(user.getUsername(),
passwordEncoder.encode(user.getPassword()),user.getEmail(),
"USER",
user.getAvatar());
User save = userRepository.save(newUser);
System.out.println("This won't pass");
return ....
}

最佳答案

我希望 Spring Boot 能够将现有验证器连接到 EntityManager ,但显然事实并非如此。

您可以使用 HibernatePropertiesCustomizer 并将属性添加到现有 EntityManagerFactoryBuilder 并注册 Validator

注意:我假设您使用的是 Spring Boot 2.0

@Component
public class ValidatorAddingCustomizer implements HibernatePropertiesCustomizer {

private final ObjectProvider<javax.validation.Validator> provider;

public ValidatorAddingCustomizer(ObjectProvider<javax.validation.Validator> provider) {
this.provider=provider;
}

public void customize(Map<String, Object> hibernateProperties) {
Validator validator = provider.getIfUnique();
if (validator != null) {
hibernateProperties.put("javax.persistence.validation.factory", validator);
}
}
}

像这样的东西应该将现有的验证器与休眠连接起来,并且它将利用自动连接。

注意:您不需要在验证器上使用@Component,在返回Validator<的实例之前, Autowiring 已构建到验证器工厂中

关于Spring Boot - Hibernate 自定义约束不注入(inject)服务,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50212117/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com