0

使用 @OneToMany 或 @ManyToOne 关系时,我的测试失败。

实体:

@Entity
@Table(name = "CONTACTS")
public class Contact implements Serializable {

    private static final long serialVersionUID = 8841543709585000683L;

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name = "CONTACT_ID")
    private Long contactId;

    @Column(name = "CONT_NAME", nullable = false)
    private String name;

    @Column(name = "LAST_NAME")
    private String lastName;

    @Column(name = "NICK_NAME")
    private String nickName;

    @OneToMany(targetEntity = TelephoneNumber.class, fetch = FetchType.EAGER, mappedBy = TelephoneNumber.CONTACT_FIELD_NAME, cascade = CascadeType.ALL)
    private Set<TelephoneNumber> telephoneNumbers = new HashSet<TelephoneNumber>(0);

    getters();
    setters()   
}

@Entity
@Table(name = "TELEPHONE_NUMBERS")
public class TelephoneNumber implements Serializable {

    private static final long serialVersionUID = 4459049334214768290L;

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name = "NUMBER_ID")
    private Long telephoneNumberId;

    @Enumerated(EnumType.ORDINAL)
    @Column(name = "TELEPHONE_TYPE", nullable = false)
    private TelephoneType telephoneType;

    @Column(name = "TELEPHONE_NUMBER")
    private String telephoneNumber;

    @JoinColumn(name = "CONTACT_ID", nullable = false)
    @ManyToOne(targetEntity = Contact.class, fetch = FetchType.EAGER, cascade = CascadeType.ALL)
    private Contact contact;
    public final static String CONTACT_FIELD_NAME = "contact";

    getters();
    setters();
}

春天上下文:

<import resource="classpath*:spring/dbs-repository-context.xml" />

<!-- Activates JPA's @PersistenceContext and @PersistenceUnit (if available) 
    annotations to be detected in bean classes. -->
<context:annotation-config />

<!-- Enable Transaction using @Transactional annotation -->
<tx:annotation-driven />

<bean id="daTM"
    class="org.springframework.jdbc.datasource.DataSourceTransactionManager"
    p:dataSource-ref="dataSource" />

<!-- Create local transaction manager -->
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager"
    p:entityManagerFactory-ref="entityManagerFactory" lazy-init="true"
    p:dataSource-ref="dataSource" />

<!-- Create EntityManagerFactory for injection into services. -->
<bean id="entityManagerFactory"
    class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean"
    p:dataSource-ref="dataSource" p:persistenceXmlLocation-ref="persistenceXmlLocation">
    <property name="jpaVendorAdapter">
        <bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
            <property name="showSql" value="true" />
        </bean>
    </property>
</bean>

<!-- Database access configuration -->
<bean id="persistenceXmlLocation" class="java.lang.String">
    <constructor-arg value="classpath*:META-INF/persistence.xml"></constructor-arg>
</bean>

<context:property-placeholder
    location="classpath:spring/jdbc.properties" />

<!-- Dev's env DataSource -->
<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"
    destroy-method="close">
    <property name="driverClassName" value="${jdbc.driver}" />
    <property name="url" value="${jdbc.url}" />
    <property name="username" value="${jdbc.username}" />
    <property name="password" value="${jdbc.password}" />
</bean>

持久性.xml:

<?xml version="1.0" encoding="UTF-8"?>
<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"
    version="2.0" xmlns="http://java.sun.com/xml/ns/persistence">
    <persistence-unit name="contactManagerPU">
        <provider>org.hibernate.ejb.HibernatePersistence</provider>

        <class>com.snp.cm.persistency.contact.Contact</class>
        <class>com.snp.cm.persistency.contact.TelephoneNumber</class>

        <exclude-unlisted-classes>false</exclude-unlisted-classes>

        <properties>
            <property name="hibernate.max_fetch_depth" value="3" />
        </properties>
    </persistence-unit>
</persistence>

并且测试失败(最后一次断言失败导致 0 个电话但存在其他字段):

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = { "classpath*:spring/dbs-application-context.xml" })
@Transactional
public class ContactRepositoryTest {

    @Autowired
    private ContactRepository contactRepository;
    @Autowired
    private TelephoneNumberRepository telephoneNumberRepository;

    @Test
    public void testRepositorySaveMethod() {
        Contact contact = new Contact();
        contact.setLastName("Carter");
        contact.setName("John");
        contact.setNickName(null);
        contact = this.contactRepository.save(contact);
        Assert.assertNotNull(contact.getContactId());

        TelephoneNumber telephoneNumber1 = new TelephoneNumber();
        telephoneNumber1.setTelephoneNumber("093 7674441");
        telephoneNumber1.setContact(contact);
        telephoneNumber1.setTelephoneType(TelephoneType.HOME);
        this.telephoneNumberRepository.save(telephoneNumber1);

        TelephoneNumber telephoneNumber2 = new TelephoneNumber();
        telephoneNumber2.setTelephoneNumber("093 7674441");
        telephoneNumber2.setContact(contact);
        telephoneNumber2.setTelephoneType(TelephoneType.MOBILE);
        this.telephoneNumberRepository.save(telephoneNumber2);

        contact = this.contactRepository.findOne(contact.getContactId());

        Assert.assertEquals(2, contact.getTelephoneNumbers().size());
    }
}

可能是什么原因?我尝试更改 FetchType 但它对我不起作用。

4

1 回答 1

0

您在测试中有两个选择:

  • 刷新以更新父实体(在“Assert.assertEquals (..”之前添加“session.flush()”)
  • 通过父实体(contact.getTelephoneNumbers().Add(entity))直接添加子实体,级联,自动关联。

问候,

于 2012-08-27T13:49:45.160 回答