2

当使用 saveOrUpdate 创建新对象时,休眠将对象存储在数据库中并正确返回。但是在该方法的同一调用中创建了一个带有一些空列的附加对象。

数据库中的对象如下所示:

id 因果 isInTopTen propability 责任范围 title
312 测试测试 0 0 NULL 0 NULL
313 测试 测试 0 2 客户 3 测试

这是数据类:

@Entity
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
@Table(name=HibernateConstants.RISK_TABLE)
public class Risk implements Serializable {

    private static final long serialVersionUID = 1L;

    @Id
    @GeneratedValue(strategy = GenerationType.TABLE)
    private int id;
    private boolean isInTopTen;
    private String title;
    private String cause;
    private String effect;
    @Enumerated(EnumType.STRING)
    private Responsibility responsibility;
    private int propability;
    private int scope;
    @OneToMany
    @LazyCollection(LazyCollectionOption.FALSE)
    @Cascade({CascadeType.SAVE_UPDATE, CascadeType.MERGE}) 
    private List<Keyword> keywords;
    @OneToMany
    @LazyCollection(LazyCollectionOption.FALSE)
    @Cascade({CascadeType.SAVE_UPDATE, CascadeType.MERGE}) 
    private List<Action> actions;
    @OneToMany
    @LazyCollection(LazyCollectionOption.FALSE)
    @Cascade({CascadeType.SAVE_UPDATE, CascadeType.MERGE}) 
    private List<ProjectRisk> derivedProjectsRisks;
}

这是我将对象存储到数据库的方式: public class DataUtils { private Session session; 私有静态 DataUtils dataUtils;

    private DataUtils() {}

    private void setSession() {
        session = HibernateSessionFactory.getInstance().getCurrentSession();
    }

    public static DataUtils getInstance() {
        if (dataUtils == null) {
            dataUtils = new DataUtils();
        }
        return dataUtils;
    }

    public void storeOne(Object o) {
        setSession();
        Transaction transaction = session.beginTransaction();
        session.saveOrUpdate(o);
        transaction.commit();
    }
}

还有我的休眠配置:

public class HibernateSessionFactory {
    // Singleton
    private HibernateSessionFactory() {}

    private static SessionFactory sessionFactory;

    public static SessionFactory getInstance() {
        if (sessionFactory==null) {
            final Configuration configuration = new Configuration();
            configuration.configure("hibernate.cfg.xml");
            ServiceRegistry serviceRegistry = new ServiceRegistryBuilder().applySettings(configuration.getProperties()).buildServiceRegistry();
            sessionFactory = configuration.buildSessionFactory(serviceRegistry);
        }
        return sessionFactory;
    }
}

<?xml version='1.0' encoding='UTF-8'?>
<!DOCTYPE hibernate-configuration PUBLIC
   "-//Hibernate/Hibernate Configuration DTD 3.0//EN"
   "http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
   <session-factory>
    <!-- DB-Connection -->
      <property name="connection.url">jdbc:jtds:sqlserver://localhost:1433/riskManagement</property>
      <property name="connection.username">riskManagement</property>
      <property name="connection.password">riskManagement</property>
      <property name="connection.driver_class">net.sourceforge.jtds.jdbc.Driver</property>
      <property name="dialect">org.hibernate.dialect.SQLServerDialect</property>
      <property name="cache.provider_class">org.hibernate.cache.EhCacheProvider</property>
      <property name="current_session_context_class">thread</property>
      <property name="hibernate.transaction.factory_class">org.hibernate.transaction.JDBCTransactionFactory</property>      

      <property name="hibernate.hbm2ddl.auto">update</property>

      <!-- Classes added to persistence -->
      <mapping class="com.encoway.riskManagement.data.Customer" />
      <mapping class="com.encoway.riskManagement.data.Keyword" />
      <mapping class="com.encoway.riskManagement.data.Project" />
      <mapping class="com.encoway.riskManagement.data.ProjectRisk" />
      <mapping class="com.encoway.riskManagement.data.Risk" />
      <mapping class="com.encoway.riskManagement.data.Action" />
   </session-factory>
</hibernate-configuration>

有关此事务的日志信息:

Opening new JDBC connection
Created connection to: jdbc:jtds:sqlserver://localhost:1433/riskManagement, Isolation Level: 2
select sequence_next_hi_value from hibernate_sequences with (updlock, rowlock) where sequence_name = 'KEYWORD'
update hibernate_sequences set sequence_next_hi_value = ? where sequence_next_hi_value = ? and sequence_name = 'KEYWORD'
Generated identifier: 4882432, using strategy: org.hibernate.id.MultipleHiLoPerTableGenerator
committing
Processing flush-time cascades
Dirty checking collections
Flushed: 1 insertions, 0 updates, 0 deletions to 1 objects
Flushed: 0 (re)creations, 0 updates, 0 removals to 0 collections
Listing entities:
com.encoway.riskManagement.data.Keyword{id=4882432, name=abc}
insert into KEYWORD (name, id) values (?, ?)
committed JDBC Connection
HHH000420: Closing un-released batch
Releasing JDBC connection
Released JDBC connection
begin
Obtaining JDBC connection
Obtained JDBC connection
initial autocommit status: false
select sequence_next_hi_value from hibernate_sequences with (updlock, rowlock) where sequence_name = 'RISK'
update hibernate_sequences set sequence_next_hi_value = ? where sequence_next_hi_value = ? and sequence_name = 'RISK'
Generated identifier: 4718592, using strategy: org.hibernate.id.MultipleHiLoPerTableGenerator
Loading entity: [com.encoway.riskManagement.data.Keyword#4882432]
select keyword0_.id as id3_0_, keyword0_.name as name3_0_ from KEYWORD keyword0_ where keyword0_.id=?
Result set row: 0
Result row: EntityKey[com.encoway.riskManagement.data.Keyword#4882432]
Resolving associations for [com.encoway.riskManagement.data.Keyword#4882432]
Done materializing entity [com.encoway.riskManagement.data.Keyword#4882432]
Done entity load
committing
Processing flush-time cascades
Dirty checking collections
Collection found: [com.encoway.riskManagement.data.Risk.actions#4718592], was: [<unreferenced>] (initialized)
Collection found: [com.encoway.riskManagement.data.Risk.derivedProjectsRisks#4718592], was: [<unreferenced>] (initialized)
Collection found: [com.encoway.riskManagement.data.Risk.keywords#4718592], was: [<unreferenced>] (initialized)
Flushed: 1 insertions, 0 updates, 0 deletions to 2 objects
Flushed: 3 (re)creations, 0 updates, 0 removals to 3 collections
Listing entities:
com.encoway.riskManagement.data.Risk{id=4718592, title=null, scope=0, keywords=[com.encoway.riskManagement.data.Keyword#4882432], cause=abc, effect=abc, derivedProjectsRisks=[], isInTopTen=false, propability=0, actions=[], responsibility=null}
com.encoway.riskManagement.data.Keyword{id=4882432, name=abc}
insert into RISK (cause, effect, isInTopTen, propability, responsibility, scope, title, id) values (?, ?, ?, ?, ?, ?, ?, ?)
Inserting collection: [com.encoway.riskManagement.data.Risk.actions#4718592]
Collection was empty
Inserting collection: [com.encoway.riskManagement.data.Risk.derivedProjectsRisks#4718592]
Collection was empty
Inserting collection: [com.encoway.riskManagement.data.Risk.keywords#4718592]
insert into RISK_KEYWORD (RISK_id, keywords_id) values (?, ?)
Done inserting collection: 1 rows inserted
committed JDBC Connection
HHH000420: Closing un-released batch
Releasing JDBC connection
Released JDBC connection
begin
Obtaining JDBC connection
Obtained JDBC connection
initial autocommit status: false
Generated identifier: 4718593, using strategy: org.hibernate.id.MultipleHiLoPerTableGenerator
committing
Processing flush-time cascades
Dirty checking collections
Collection found: [com.encoway.riskManagement.data.Risk.actions#4718593], was: [<unreferenced>] (initialized)
Collection found: [com.encoway.riskManagement.data.Risk.derivedProjectsRisks#4718593], was: [<unreferenced>] (initialized)
Collection found: [com.encoway.riskManagement.data.Risk.keywords#4718593], was: [<unreferenced>] (initialized)
Flushed: 1 insertions, 1 updates, 0 deletions to 2 objects
Flushed: 3 (re)creations, 0 updates, 0 removals to 3 collections
Listing entities:
com.encoway.riskManagement.data.Risk{id=4718593, title=abc, scope=3, keywords=[com.encoway.riskManagement.data.Keyword#4882432], cause=abc, effect=abc, derivedProjectsRisks=[], isInTopTen=false, propability=2, actions=[], responsibility=CUSTOMER}
com.encoway.riskManagement.data.Keyword{id=4882432, name=abc}
insert into RISK (cause, effect, isInTopTen, propability, responsibility, scope, title, id) values (?, ?, ?, ?, ?, ?, ?, ?)
update KEYWORD set name=? where id=?
Inserting collection: [com.encoway.riskManagement.data.Risk.actions#4718593]
Collection was empty
Inserting collection: [com.encoway.riskManagement.data.Risk.derivedProjectsRisks#4718593]
Collection was empty
Inserting collection: [com.encoway.riskManagement.data.Risk.keywords#4718593]
insert into RISK_KEYWORD (RISK_id, keywords_id) values (?, ?)
Done inserting collection: 1 rows inserted
committed JDBC Connection
HHH000420: Closing un-released batch
Releasing JDBC connection
Released JDBC connection
4

1 回答 1

1

正如评论中已经提到的:“我解决了这个问题。在保存之前还有另一个类调用 session.merge() 并导致了额外的对象。” 所以这只是一个单独的错误。

于 2013-03-21T20:51:02.663 回答