2013-02-20 16 views
9

Bu soruya şuna bir iz gelir: JPA ConstraintViolation vs RollbackBean Validation API ile birleştirildiğinde, JPA spesifikasyonlarını takip etmiyor musunuz?

JPA ve doğrulama API'sinin (JSR-303) birleşimiyle ilgili bazı testler yaptım.

I (sayfa 101-102) JPA specifications aşağıdaki bulundu: Varsayılan olarak

, varsayılan Bean Doğrulama grubu (grup Varsayılan) ön inat ve ön güncelleme yaşam döngüsü doğrulama üzerine doğrulanır ConstraintViolation kümesi validate yöntemi tarafından döndürülen nesnelerin ise olaylar

...

boş değil, kalıcılık sağlayıcısı ConstraintV döndürülen setine bir başvuru içeren javax.validation.ConstraintViolationException atmak gerekir iolation nesneleri ve geri alma işlemini işaretlemelidir.

ben kurulumun şöyle testi: olarak

  • HibernateValidator JSR-303 uygulama
  • 2 PersistenceProvider Hibernate ve EclipseLink
  • bir varsayılan stratejisi (@Generated) ve @NotNull String name ile üretilen bir kimliğe sahip varlık NameNotNullWithDefaultGeneratedStrategy Tablo stratejisiyle oluşturulan bir kimlikle
  • başka bir varlık NameNotNullWithTableGeneratedStrategy ()) ve @NotNull String name sütunu
  • testinde, null değerine sahip her varlığın bir örneğini persist deneyin.
  • beklenen sonuçlar, perspektif yöntemle atılan javax.validation.ConstraintViolationException ve rollback only olarak işaretlenen işlemdir (yani, bu varsayımlar, bu yayında belirtilen JPA spesifikasyonuna dayanmaktadır).

sonuçlar şöyle:

  • bir sağlayıcısı olarak tutulması bağlantı ile:
    • persist yöntem hem kurumlara yönelik javax.validation.ConstraintViolationException atar.
    • işlem iki durumda sağlayıcısı olarak hazırda ile
  • içinde rollback only olarak işaretlenmiş:
    • persistNameNotNullWithDefaultGeneratedStrategy + işlem
    • persist herhangi atmayın rollback only olarak işaretlenmiş varlık için javax.validation.ConstraintViolationException atar varlık NameNotNullWithTableGeneratedStrategy + için işlem , işaretini rollback only
    • olarak işaretlemedi

      • gerçekten JPA şartname ihlalidir: NameNotNullWithTableGeneratedStrategy için
      • commit soru vardır bir RollbackException

    ile başarısız? ya da tablonun oluşturduğu stratejinin özel durumuyla ilgili bir şey eksik miyim? Bir ihlali olması durumunda: İlgili herhangi bir hata raporu var mı?

    package com.example.jpa.validator; 
    import org.junit.Assert; 
    import org.junit.Test; 
    import javax.persistence.EntityManager; 
    import javax.persistence.EntityManagerFactory; 
    import javax.persistence.EntityTransaction; 
    import javax.persistence.Persistence; 
    import javax.persistence.RollbackException; 
    
    public class ConstraintViolationExceptionTest { 
    
        @Test 
        public void testHibernateDefaultStrategy() { // Success 
         testPersistWithNullName("pu-hibernate",new NameNotNullWithDefaultGeneratedStrategy()); 
        } 
    
        @Test 
        public void testHibernateTableStrategy() { 
         testPersistWithNullName("pu-hibernate",new NameNotNullWithTableGeneratedStrategy()); 
         //this test fail with : 
         //java.lang.AssertionError: Expecting a javax.validation.ConstraintViolationException, but persist() succeed ! 
        } 
    
        @Test 
        public void testEclipseLinkDefaultStrategy() { // Success 
         testPersistWithNullName("pu-eclipselink",new NameNotNullWithDefaultGeneratedStrategy()); 
        } 
    
        @Test 
        public void testEclipseLinkTableStrategy() { // Success 
         testPersistWithNullName("pu-eclipselink",new NameNotNullWithTableGeneratedStrategy()); 
        } 
    
        private void testPersistWithNullName(String persistenceUnitName, Object entity){ 
         EntityManagerFactory emf = Persistence.createEntityManagerFactory(persistenceUnitName); 
         EntityManager entityManager = emf.createEntityManager(); 
         try { 
          final EntityTransaction transaction = entityManager.getTransaction(); 
          transaction.begin(); 
          try { 
           try { 
            entityManager.persist(entity); 
            Assert.fail("Expecting a javax.validation.ConstraintViolationException, but persist() succeed !"); 
           } catch (javax.validation.ConstraintViolationException cve) { 
            //That's expected 
            Assert.assertTrue("According JPA specs transaction must be flagged as rollback only",transaction.getRollbackOnly()); 
           } catch (Exception e) { 
            Assert.assertTrue("According JPA specs transaction must be flagged as rollback only",transaction.getRollbackOnly()); 
            e.printStackTrace(); 
            Assert.fail("Expecting a javax.validation.ConstraintViolationException, but got " + e.getClass()); 
           } 
           transaction.commit(); 
           Assert.fail("persisted with null name !!!"); 
          } catch (RollbackException e) { 
           //That's expected 
          } catch (Exception e) { 
           e.printStackTrace(); 
           Assert.fail("Unexpected exception :"+e.getMessage()); 
          } 
         } finally { 
          entityManager.close(); 
         } 
        } 
    } 
    

    kişiler

    Standart strateji

    package com.example.jpa.validator; 
    
    import javax.persistence.Entity; 
    import javax.persistence.GeneratedValue; 
    import javax.persistence.Id; 
    import javax.validation.constraints.NotNull; 
    
    @Entity 
    public class NameNotNullWithDefaultGeneratedStrategy { 
    
        @Id @GeneratedValue private Long id; 
        @NotNull public String name; 
        public NameNotNullWithDefaultGeneratedStrategy() {} 
    } 
    

    Tablo stategy:

    package com.example.jpa.validator; 
    
    import javax.persistence.Entity; 
    import javax.persistence.GeneratedValue; 
    import javax.persistence.GenerationType; 
    import javax.persistence.Id; 
    import javax.persistence.TableGenerator; 
    import javax.validation.constraints.NotNull; 
    
    @Entity 
    public class NameNotNullWithTableGeneratedStrategy { 
    
        @GeneratedValue(strategy = GenerationType.TABLE, 
         generator = "NAME_MUST_NOT_BE_NULL_ID_GENERATOR") 
        @TableGenerator(name = "NAME_MUST_NOT_BE_NULL_ID_GENERATOR") 
        @Id @NotNull private Long id; 
        @NotNull public String name; 
        public NameNotNullWithTableGeneratedStrategy() {} 
    } 
    
    İşte

benim test için koddur

persistence.xml

<?xml version="1.0" encoding="UTF-8"?> 
    <persistence version="2.0" xmlns="http://java.sun.com/xml/ns/persistence" 
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
     xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd"> 
     <persistence-unit name="pu-hibernate" transaction-type="RESOURCE_LOCAL"> 
      <provider>org.hibernate.ejb.HibernatePersistence</provider> 
      <class>com.example.jpa.validator.NameNotNullWithTableGeneratedStrategy</class> 
      <class>com.example.jpa.validator.NameNotNullWithDefaultGeneratedStrategy</class> 
      <properties> 
       <property name="javax.persistence.jdbc.driver" value="org.h2.Driver"/> 
       <property name="javax.persistence.jdbc.url" value="jdbc:h2:mem:test_mem_hibernate"/> 
       <property name="hibernate.hbm2ddl.auto" value="create-drop"/> 
       <property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/> 
      </properties> 
     </persistence-unit> 
     <persistence-unit name="pu-eclipselink" transaction-type="RESOURCE_LOCAL"> 
      <provider>org.eclipse.persistence.jpa.PersistenceProvider</provider> 
      <class>com.example.jpa.validator.NameNotNullWithTableGeneratedStrategy</class> 
      <class>com.example.jpa.validator.NameNotNullWithDefaultGeneratedStrategy</class> 
      <properties> 
       <property name="javax.persistence.jdbc.driver" value="org.h2.Driver"/> 
       <property name="javax.persistence.jdbc.url" value="jdbc:h2:mem:test_mem"/> 
       <property name="eclipselink.ddl-generation" value="create-tables"/> 
       <property name="eclipselink.target-database" value="org.eclipse.persistence.platform.database.H2Platform"/> 
      </properties> 
     </persistence-unit> 
    </persistence> 

Bunun için bir hata raporu yayımlandı

<?xml version="1.0" encoding="UTF-8"?> 
    <project xmlns="http://maven.apache.org/POM/4.0.0" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> 
     <modelVersion>4.0.0</modelVersion> 

     <groupId>com.example</groupId> 
     <artifactId>com.example.jpa.validator</artifactId> 
     <version>1.0-SNAPSHOT</version> 
     <properties> 
      <hibernate.version>4.2.0.CR1</hibernate.version> 
      <hibernate-validator.version>4.3.1.Final</hibernate-validator.version> 
      <junit.version>4.11</junit.version> 
      <h2.version>1.3.170</h2.version> 
     </properties> 

     <dependencies> 
      <dependency> 
       <groupId>org.hibernate</groupId> 
       <artifactId>hibernate-validator</artifactId> 
       <version>${hibernate-validator.version}</version> 
      </dependency> 
      <dependency> 
       <groupId>com.h2database</groupId> 
       <artifactId>h2</artifactId> 
       <version>${h2.version}</version> 
       <scope>test</scope> 
      </dependency> 
      <dependency> 
       <groupId>junit</groupId> 
       <artifactId>junit</artifactId> 
       <scope>test</scope> 
       <version>${junit.version}</version> 
      </dependency> 

      <dependency> 
       <groupId>org.hibernate</groupId> 
       <artifactId>hibernate-core</artifactId> 
       <version>${hibernate.version}</version> 
      </dependency> 
      <dependency> 
       <groupId>org.hibernate</groupId> 
       <artifactId>hibernate-entitymanager</artifactId> 
       <version>${hibernate.version}</version> 
      </dependency> 

      <dependency> 
       <groupId>org.eclipse.persistence</groupId> 
       <artifactId>org.eclipse.persistence.jpa</artifactId> 
       <version>2.4.0</version> 
      </dependency> 
      <dependency> 
       <groupId>org.eclipse.persistence</groupId> 
       <artifactId>javax.persistence</artifactId> 
       <version>2.0.0</version> 
      </dependency> 
     </dependencies> 

     <repositories> 
      <repository> 
       <url>http://download.eclipse.org/rt/eclipselink/maven.repo/</url> 
       <id>eclipselink</id> 
       <layout>default</layout> 
       <name>Repository for library EclipseLink (JPA 2.0)</name> 
      </repository> 
     </repositories> 
    </project> 
+1

@column (ne yapılmaktadır = false null) @NotNull ile birlikte mi? –

+0

'@Column (nullable = false)' ile denedim: aynı sonuç – ben75

+1

Gerçekten de neden üretim stratejisinin bu durumda doğrulamayı etkilediğini anlamıyorum, ancak bir test raporunu zaten yaptığınız gibi bir hata raporunu kesinlikle açacağım hazırda bekletme bölümünün ardından hazırda bekletme-validator'a karşı. –

cevap

İlgili konular