Hibernate无法反序列化错误

时间:2013-12-29 03:35:04

标签: java hibernate

我有这个Oracle表:

SQL>  Name                                         Null?    Type
 ----------------------------------------- -------- ----------------------------
 JOB_ID                                    NOT NULL VARCHAR2(13)
 TYPE                                      NOT NULL NUMBER
 COMPONENT_DESCRIPTION                     NOT NULL VARCHAR2(255)
 COMPONENT_ID                                       VARCHAR2(13)
 STATUS                                    NOT NULL NUMBER(1)
 REASON                                             VARCHAR2(255)
 NOTES                                              VARCHAR2(255)

SQL>

没有定义的主键,但组合的JOB_ID,TYPE和COMPONENT_DESCRIPTION是唯一的。我不能对数据库结构进行任何更改,而我正在工作的代码只能从DB中读取,它永远不会写入它。

我制作了这个Hibernate地图文件:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-mapping PUBLIC 
    "-//Hibernate/Hibernate Mapping DTD 3.0//EN" 
    "classpath://org/hibernate/hibernate-mapping-3.0.dtd">
<hibernate-mapping schema="ARCHIVE">

<class name="myclass.ArchiveJobHeaderComponents" table="JOB_HEADER_COMPONENTS">
    <composite-id>
        <key-property name="jobId" column="JOB_ID" type="java.lang.String" />
        <key-property name="type" column="TYPE" type="java.lang.Number" />
        <key-property name="componentDescription" column="COMPONENT_DESCRIPTION" type="java.lang.String" />
    </composite-id>
    <property name="componentId" column="COMPONENT_ID" type="java.lang.String" not-null="false" />
    <property name="status" column="STATUS" type="java.lang.Number" />
    <property name="reason" column="REASON" type="java.lang.String" not-null="false" />
    <property name="notes" column="NOTES" type="java.lang.String" not-null="false" />
</class>

<query name="JobHeaderComponents.lookupJobHeaderComponents">
    <![CDATA[from myclass.ArchiveJobHeaderComponents where
               jobId = :jobId and
               type = :type and
               componentDescription = :componentDescription ]]>
</query>

<query name="JobHeaderComponents.listJobHeaderComponentsByComponentId">
    <![CDATA[from myclass.ArchiveJobHeaderComponents where componentId = :id]]>
</query>

</hibernate-mapping>

这是相应的Java类文件:

package myclass;

import org.apache.commons.lang.builder.EqualsBuilder;
import org.apache.commons.lang.builder.HashCodeBuilder;
import org.apache.commons.lang.builder.ToStringBuilder;

import java.io.Serializable;
import java.lang.Number;
import java.util.HashSet;

public class ArchiveJobHeaderComponents implements Serializable {

    private String jobId;
    private Number type;
    private String componentDescription;
    private String componentId;
    private Number status;
    private String reason;
    private String notes;

    public String getJobId() {
        return jobId;
    }

    public void setJobId(String jobId) {
        this.jobId = jobId;
    }

    public Number getType() {
        return type;
    }

    public void setType(Number type) {
        this.type = type;
    }

    public String getComponentDescription() {
        return componentDescription;
    }

    public void setComponentDescription(String componentDescription) {
        this.componentDescription = componentDescription;
    }

    public String getComponentId() {
        return componentId;
    }

    public void setComponentId(String componentId) {
        this.componentId = componentId;
    }

    public Number getStatus() {
        return status;
    }

    public void setStatus(Number status) {
        this.status = status;
    }

    public String getReason() {
        return reason;
    }

    public void setReason(String reason) {
        this.reason = reason;
    }

    public String getNotes() {
        return notes;
    }

    public void setNotes(String notes) {
        this.notes = notes;
    }

    public int hashCode() {
       return new HashCodeBuilder().
                           append(getJobId()).
                           append(getType()).
                           append(getComponentDescription()).
                           append(getComponentId()).
                           append(getStatus()).
                           append(getReason()).
                           append(getNotes()).toHashCode();
    }

    public boolean equals(Object o) {
        if (this == o) {
            return true;
        }
        if (!(o instanceof ArchiveJobHeaderComponents)) {
            return false;
        }
        ArchiveJobHeaderComponents that = (ArchiveJobHeaderComponents) o;
        return new EqualsBuilder().append(this.getJobId(), that.getJobId()).
                           append(this.getType(), that.getType()).
                           append(this.getComponentDescription(), that.getComponentDescription()).
                           append(this.getComponentId(), that.getComponentId()).
                           append(this.getStatus(), that.getStatus()).
                           append(this.getReason(), that.getReason()).
                           append(this.getNotes(), that.getNotes()).isEquals();
    }

    public String toString() {
        return new ToStringBuilder(this).
                           append("jobId", getJobId()).
                           append("type", getType()).
                           append("componentDescription", getComponentDescription()).
                           append("componentId", getComponentId()).
                           append("status", getStatus()).
                           append("reason", getReason()).
                           append("notes", getNotes()).toString();
    }

}

每当我从查询中获取数据时,我都会得到“无法反序列化”,然后出现“EOFException”错误。

我已经检查过了:
- 序列化类型的Java类中没有变量 - Java类正在实现Serializable

我不想将三列(JOB_ID,TYPE和COMPONENT_DESCRIPTION)拆分为单独的“Id”类,因为我对如何访问数据存在概念上的问题。 (我意识到这不是推荐但是支持)。

任何人都可以指出我在实施这个方面做错了吗?

由于

编辑:
我已经将hbm.xml更改为没有复合键,只是JOB_ID上的id而没有任何改进 我已将not-null =“false”添加到可以为空的列中,也没有改进。

2 个答案:

答案 0 :(得分:8)

实际上,看一下代码和Hibernate映射文件,我认为问题是你试图将列TYPESTATUS映射到NumberNumber是一个抽象类,因此无法直接实例化。

由于TYPESTATUS都是NOT NULL,我会使用原始Java类型来存储它们的值,例如:

public class ArchiveJobHeaderComponents implements Serializable {

  private String jobId;
  private int type; // int should give you a large enough range - but change to long if required
  private String componentDescription;
  private String componentId;
  private boolean status; // status appears to be a boolean (NUMBER(1))
  private String reason;
  private String notes;
  // remainder omitted
}

另外,请记得更新Hibernate映射文件以反映上面的内容!!

答案 1 :(得分:0)

如果其他人正在使用传统的Hibernate(3.0)应用程序,导致此错误的其他因素是使用Java 8和OJDBC 1.4运行应用程序。升级到OJDBC 6解决了它。