如何使用 Spring + Hibernate 对实体进行自定义验证以进行多租户设置
Posted
技术标签:
【中文标题】如何使用 Spring + Hibernate 对实体进行自定义验证以进行多租户设置【英文标题】:How to do custom validation on entity for multitenant setup using Spring + Hibernate 【发布时间】:2021-03-12 05:22:08 【问题描述】:我正在尝试使用 spring hibernate 在多租户设置中使用自定义 ConstraintValidator 实现来验证实体的字段。 我们如何让自定义验证器租户知道?验证器中的实体管理器和其他自动装配的 bean 始终为空。
实体类:
@Entity
@Table(name = "autoupdate_json")
public class AutoupdateJson
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private long id;
@Column(name="autoupdate_id")
private String autoupdateId;
@Column(name="deployment_json", length=10000)
@ValidateAutodeploymentConfig
@Convert(converter=JpaConverterJson.class)
private ApplyInputJson deploymentJson;
` 验证注解:
@Documented
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = AutodeploymentConfigValidator.class)
public @interface ValidateAutodeploymentConfig
String message() default "One or More of the Devices already have perpetual mode settings enabled. Please cancel the existing "
+ " deployment config to add a new one, Updates are not supported. ";
Class<?>[] groups() default ;
Class<? extends Payload>[] payload() default ;
验证器实现:
public class AutodeploymentConfigValidator
implements ConstraintValidator<ValidateAutodeploymentConfig, ApplyInputJson>
@PersistenceContext
EntityManager entityManager;
@Autowired
DeviceRepository deviceRepository;
@Override
public boolean isValid(ApplyInputJson value, ConstraintValidatorContext context)
List<String> deviceSerialNumbers = Arrays.asList(value.getDevices().getSerial());
System.out.println("entityManager: " + entityManager);
System.out.println("repo bean: " + deviceRepository);
两个系统输出都是空的。
【问题讨论】:
【参考方案1】:实体管理器和设备存储库为空,因为 AutodeploymentConfigValidator
不是来自 Spring 上下文。
它是由hibernate使用的默认约束验证工厂创建的,它不使用arg构造函数。
尝试添加HibernatePropertiesCustomizer
来告诉hibernate 使用哪个验证工厂。比如:
@Component
public class HibernateCustomizer implements HibernatePropertiesCustomizer
private final ValidatorFactory validatorFactory;
public HibernateCustomizer(ValidatorFactory validatorFactory)
this.validatorFactory = validatorFactory;
public void customize(Map<String, Object> hibernateProperties)
hibernateProperties.put("javax.persistence.validation.factory", validatorFactory);
有了这个,你应该能够在你的约束验证器中使用实体管理器。
【讨论】:
以上是关于如何使用 Spring + Hibernate 对实体进行自定义验证以进行多租户设置的主要内容,如果未能解决你的问题,请参考以下文章
使用 Hibernate + Spring 进行缓存 - 一些问题
对使用 Spring 和 Hibernate 的 Java 日志系统感到困惑
使用 Spring Boot + Hibernate + MySql 运行 MVC 应用程序