休眠错误:在hbm2java代码上混合可为空和不可为空的属性

Joh*_*zen 5 hibernate hbm2java hibernate-annotations hibernate3-maven-plugin

我正在使用hibernate3-maven-plugin来查询Oracle10g数据库并使用hbm2java目标生成带有JPA批注的Java类。然后,我使用spring配置一个会话工厂,该工厂扫描带注释的代码。

经过长时间的努力hbm2java,我设法生成了类,但现在又遇到了另一个问题:加载带注释的类时,出现“不允许在属性中混合可为空和不可为空的列”的异常。

数据库定义表FOO和BAR如下:

CREATE TABLE FOO (
  STATUS_CODE ... NOT NULL,
  REASON_CODE ...);

ALTER TABLE FOO ADD (
  CONSTRAINT FK_BAR
  FOREIGN KEY (REASON_CODE, STATUS_CODE)
  REFERENCES BAR(REASON_CODE, STATUS_CODE));

CREATE TABLE BAR (
  STATUS_CODE ... NOT NULL,
  REASON_CODE ... NOT NULL);

ALTER TABLE BAR (
  PRIMARY KEY (REASON_CODE, STATUS_CODE));
Run Code Online (Sandbox Code Playgroud)

因此,表FOO具有两列,它们是表BAR中的外键。列FOO.STATUS_CODE必须为非空,但列FOO.REASON_CODE可以为空。这里的逻辑是FOO需要一个状态,但并非每个状态都需要一个原因。

表BAR具有列BAR.REASON_CODE和BAR.STATUS_CODE,它们都不为空。此处的逻辑将各种(但不是全部)状态代码的原因关联在一起。因此,例如,如果状态为“已取消”,则原因可能是“欺诈”,“无能”等。

注意,诸如“活动”的状态没有任何关联的原因,因此在表BAR中不存在,但是它可以作为状态代码出现在表FOO中(没有关联的原因代码)。但是,如果FOO中的行的状态代码为“已取消”,则它还必须具有表BAR中为该状态定义的原因代码之一。

因此,表定义对我来说似乎不错(尽管我不是数据库专家)。

现在hbm2java,maven中的目标为表FOO生成以下代码:

private Bar bar;

@ManyToOne(fetch=FetchType.LAZY)
@JoinColumns( { 
    @JoinColumn(name="REASON_CODE", referencedColumnName="REASON_CODE"), 
    @JoinColumn(name="STATUS_CODE", referencedColumnName="STATUS_CODE", nullable=false) } )
public Bar getBar() {
    return this.bar;
}
Run Code Online (Sandbox Code Playgroud)

请注意,这里只有STATUS_CODE列不可为空。

但是,当创建休眠会话工厂bean并扫描带注释的类时,生成“不允许在属性中混合可为空和不可为空的列”的异常。

Caused by: org.hibernate.AnnotationException: Mixing nullable and non nullable columns in a property is not allowed: com.whatever.domain.LnrPermissionlnrPermStatusReason
  at org.hibernate.cfg.Ejb3Column.checkPropertyConsistency(Ejb3Column.java:514)
  at org.hibernate.cfg.AnnotationBinder.bindManyToOne(AnnotationBinder.java:2568)
  at org.hibernate.cfg.AnnotationBinder.processElementAnnotations(AnnotationBinder.java:1527)
  at org.hibernate.cfg.AnnotationBinder.processIdPropertiesIfNotAlready(AnnotationBinder.java:769)
  at org.hibernate.cfg.AnnotationBinder.bindClass(AnnotationBinder.java:733)
  at org.hibernate.cfg.AnnotationConfiguration.processArtifactsOfType(AnnotationConfiguration.java:636)
Run Code Online (Sandbox Code Playgroud)

这是休眠注释处理代码引起的有效错误(在这种情况下,数据库中的表定义需要更改),还是无效?如果是后者,是否可以将会话工厂代码配置为忽略此类错误?

组态

Maven依赖项:

  • org.hibernate / hibernate-core / 3.5.6-Final
  • org.hibernate / hibernate-annotations / 3.5.6-Final
  • org.springframework / spring-orm / 3.1.2-RELEASE

Spring应用程序上下文:

<bean id="sessionFactory" class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean">
    <property name="dataSource" ref="dataSource"/>
    <property name="packagesToScan" value="com.whatever.domain" />
</bean>
Run Code Online (Sandbox Code Playgroud)