JPA实体validation

好的,我正在尝试在Java EE容器中设置应用程序。 我使用JPA进行持久化,我也使用javax.validation.constraints.*约束。 默认情况下,容器在@PrePersist@PreUpdate生命周期事件期间validation实体,这对我有好处,但是如何处理ConstraintViolationException

我找不到任何文档,欢迎任何建议。

好吧,你可以抓住它:)这是一个例子(来自unit testing):

 public class CustomerTest { private static EntityManagerFactory emf; private EntityManager em; @BeforeClass public static void createEntityManagerFactory() { emf = Persistence.createEntityManagerFactory("MyPu"); } @AfterClass public static void closeEntityManagerFactory() { emf.close(); } @Before public void beginTransaction() { em = emf.createEntityManager(); em.getTransaction().begin(); } @After public void rollbackTransaction() { if (em.getTransaction().isActive()) { em.getTransaction().rollback(); } if (em.isOpen()) { em.close(); } } @Test public void nameTooShort() { try { Customer customer = new Customer("Bo"); em.persist(customer); em.flush(); fail("Expected ConstraintViolationException wasn't thrown."); } catch (ConstraintViolationException e) { assertEquals(1, e.getConstraintViolations().size()); ConstraintViolation violation = e.getConstraintViolations().iterator().next(); assertEquals("name", violation.getPropertyPath().toString()); assertEquals(Size.class, violation.getConstraintDescriptor().getAnnotation().annotationType()); } } } 

我的客户看起来像:

 @Entity public class Customer { @Id @GeneratedValue @NotNull private Long id; @NotNull @Size(min = 3, max = 80) private String name; private boolean archived; ... } 

但这只是展示API的一小部分的一个例子。

在我看来,你应该在视图级别实际处理validation。 许多演示框架支持Beanvalidation:JSF 2.0,Wicket,Spring MVC ……

也可以看看

  • 6.3。 表示层validation
  • Spring MVC,Spring Beanvalidation框架和validation确认密码/确认电子邮件字段。
  • Wicket JSR-303validation器
  • TOTD#123:f:ajax,JSF的Beanvalidation,JSF的CDI和JPA 2.0 Criteria API

您可以像Pascal描述的那样捕获ConstraintViolationException ,但请注意,在您的create / update语句之后以及事务结束之前(参见FlushModeType ),可以随时抛出此exception。 典型的抛出点是在您创建/更新语句之后或在显式flush()语句(您应谨慎使用)时读取的内容。