使用Oracle和Hibernate的单表继承策略(或每个类层次结构的表)

时间:2015-08-27 12:10:58

标签: java database oracle hibernate inheritance

我使用的是JEE6,Oracle数据库11g和Hibernate。我试图使以下继承工作:

enter image description here

因此,WikiNotification和TodoNotification扩展了通知。 根据单表继承策略,数据库中的这三个类将只有一个和一个表。

这是通知:

@Entity
@ForceDiscriminator
@Inheritance(strategy=InheritanceType.SINGLE_TABLE)
@DiscriminatorColumn(name="NOTIFICATION_TYPE")
@Table(name="SMH_NOTIFICATION")
public class Notification extends AbstractPersistentObject{

    /**
     * 
     */
    private static final long serialVersionUID = -2313098389774322743L;

    @ManyToOne
    @JoinColumn(name="RECEIVER_ID", nullable=false)
    private Userprofile receiver;


    @Column(name="CLASSIFICATION",nullable = true, length=30)
    private String classification;

    @Column(name="DESCRIPTION", nullable = true, length=60)
    private String description;

    @Column(name="DEADLINE")
    @Temporal(TemporalType.DATE)
    private Date deadline;

这是WikiNotification:

//@Entity
@DiscriminatorValue("Wiki")
//@Table(name="SMH_NOTIFICATION")
//@Inheritance(discriminatorValue="Wiki")
public class WikiNotification extends Notification{

    /**
     * 
     */
    private static final long serialVersionUID = 5025643991898983953L;


    //the sender is the user who triggers the notification
    //for example, it can the one who modifies someone else's chapters
    @ManyToOne
    @JoinColumn(name="SENDER_ID", nullable=false)
    private Userprofile sender;

    //"0" if the owner has not accepted yet, "1" if he accepted
    @Column(name="ACCEPTED", length=1, nullable=false)
    private String accepted;

    //the notification type can be "delete", "submit" or "modify"
    @Column(name="NOTIFICATIONTYPE",length=20,nullable=false)
    private String notificationType;

    //mofications, deletions and submissions are related to this article chapter
    @ManyToOne
    @JoinColumn(name="ARTICLECHAPTER",nullable=false)
    private ArticleChapter chapter;

和TodoNotification:

//@Entity
@DiscriminatorValue("Todo")
//@Table(name="SMH_NOTIFICATION")
public class TodoNotification extends Notification{

    /**
     * 
     */
    private static final long serialVersionUID = 2482841237595539431L;

    @OneToOne
    @JoinColumn(name="TODO_ID", nullable=false)
    private ToDo todo;

目前无效的是:

  • 我有一张桌子' SMH_NOTIFICATION'创造了但我没有看到 鉴别器列' NOTIFICATION_TYPE'而且我没有其他专栏用于WikiNotification和TodoNotification:

enter image description here

  • 当我在WikiNotification和TodoNotification类中编写@Entity时,我在我的数据库中创建了两个表Wikinotification和Todonotification,这不是我所期望的。应该只有一个表格' SMH_NOTIFICATION'

我尝试了以下教程,但它还没有工作:

http://www.dineshonjava.com/p/implementing-inheritance-in-hibernate.html#.Vd71ZiXtlHw

https://en.wikibooks.org/wiki/Java_Persistence/Inheritance

http://www.thejavageek.com/2014/05/14/jpa-single-table-inheritance-example/

http://uaihebert.com/jpa-mini-book-first-steps-and-detailed-concepts/13/

http://viralpatel.net/blogs/hibernate-inheritence-table-per-hierarchy-mapping/

修改

当我将Notification设为 abstract 类时,当我在WikiNotification和TodoNotification中添加 @Entity 时,我在Eclipse中获得以下几行:

    INFO  27.08.15 14:45:34.996  org.hibernate.tool.hbm2ddl.DatabaseMetadata@getTableMetadata: table not found: TodoNotification
    INFO  27.08.15 14:45:35.001  org.hibernate.tool.hbm2ddl.DatabaseMetadata@getTableMetadata: table not found: WikiNotification
    INFO  27.08.15 14:45:35.007  org.hibernate.tool.hbm2ddl.DatabaseMetadata@getTableMetadata: table not found: TodoNotification
    INFO  27.08.15 14:45:35.012  org.hibernate.tool.hbm2ddl.DatabaseMetadata@getTableMetadata: table not found: WikiNotification

所以我的数据库中有两个表,WikiNotification和TodoNotification,而我只期望一个表,因为单表继承策略。

    <hibernate-configuration>
 <session-factory>
        <property name="hibernate.show_sql">false</property>
        <property name="hibernate.format_sql">false</property>
        <property name="hibernate.bytecode.use_reflection_optimizer">false</property>
        <!--  
        <property name="current_session_context_class">thread</property>
        -->
        <property name="hibernate.hbm2ddl.auto">update</property>

       <!-- 
        <property name="hibernate.show_sql">true</property>
        <property name="hibernate.format_sql">true</property>
        <property name="hibernate.use_sql_comments">true</property>
         -->
 </session-factory>
</hibernate-configuration>

DAO配置文件:

<tx:annotation-driven transaction-manager="transactionManager" />

<bean id="transactionManager"
    class="org.springframework.orm.hibernate3.HibernateTransactionManager">
    <property name="sessionFactory">
        <ref local="sessionFactory" />
    </property>
</bean>

<bean id="sessionFactory"
    class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean">
    <property name="hibernateProperties">
        <props>
            <!-- Hibernate dialect can be defined in application context -->
            <prop key="hibernate.dialect">%{smh.hibernate.dialect}</prop>
            <prop key="hibernate.show_sql">false</prop> 
            <prop key="hibernate.hbm2ddl.auto">update</prop> 
            <prop key="hibernate.connection.SetBigStringTryClob">true</prop>
            <prop key="hibernate.jdbc.batch_size">0</prop>
        </props>
    </property>
    <property name="dataSource" ref="dataSource" />
    <property name="packagesToScan">
        <list>
            <value>com.smh.core.domain</value>
            <!--
                <value>com.seti.core.domain.entity.task.Task</value>
            -->
        </list>
    </property>
</bean>
<bean id="multipartResolver"
    class="org.springframework.web.multipart.commons.CommonsMultipartResolver">

    <!-- one of the properties available; the maximum file size in bytes -->
    <property name="maxUploadSize" value="50000000" />
</bean>

<bean id="persistenceExceptionTranslationPostProcessor"  


class="org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor" />

1 个答案:

答案 0 :(得分:0)

您需要做几件事:

  1. 确保您使用的任何方言都符合您的Oracle版本。
  2. 您需要在所有三个类上添加 @Entity
  3. 您需要提供所有类的映射到 hibermate.cfg 文件
  4. 您需要从子类中删除“nullable = false”,因为当 Discriminator.Value =“Wiki”时,“TODO_ID”将为null WikiNotification 成员值将为 Discriminator.Value =“Todo”
  5. 试一试,不要将 hibernate.hbm2ddl.auto 设置为更新,请尝试将其设置为“创建”,然后检查结果