Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/395.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/hibernate/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 非法尝试将集合与两个打开的会话关联_Java_Hibernate_Spring_Transactions - Fatal编程技术网

Java 非法尝试将集合与两个打开的会话关联

Java 非法尝试将集合与两个打开的会话关联,java,hibernate,spring,transactions,Java,Hibernate,Spring,Transactions,我正在尝试将一个pojo添加到另一个pojo中的集合中。我敢肯定,我在某些方面犯了一个非常愚蠢的错误,但我不知道如何解决它 我有一个pojo LookupTable,其中包含列列表: public class LookupTable { private long id; // More properties go here... private List<Column> columns; public void addColumn(Column column) {

我正在尝试将一个pojo添加到另一个pojo中的集合中。我敢肯定,我在某些方面犯了一个非常愚蠢的错误,但我不知道如何解决它

我有一个pojo LookupTable,其中包含列列表:

public class LookupTable {
  private long id;
  // More properties go here...
  private List<Column> columns;

  public void addColumn(Column column) {
    this.columns.add(column);
  }

  // More methods go here...
}
变量lookupTableDao在这里指的是一个简单的DAO类,它扩展了HibernateDaoSupport

我得到的错误是:

org.hibernate.HibernateException: Illegal attempt to associate a collection with two open sessions
  at org.hibernate.collection.AbstractPersistentCollection.setCurrentSession(AbstractPersistentCollection.java:410)
  at org.hibernate.event.def.OnUpdateVisitor.processCollection(OnUpdateVisitor.java:43)
  at org.hibernate.event.def.AbstractVisitor.processValue(AbstractVisitor.java:101)
  at org.hibernate.event.def.AbstractVisitor.processValue(AbstractVisitor.java:61)
  at org.hibernate.event.def.AbstractVisitor.processEntityPropertyValues(AbstractVisitor.java:55)
  at org.hibernate.event.def.AbstractVisitor.process(AbstractVisitor.java:123)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.performUpdate(DefaultSaveOrUpdateEventListener.java:293)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.entityIsDetached(DefaultSaveOrUpdateEventListener.java:223)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.performSaveOrUpdate(DefaultSaveOrUpdateEventListener.java:89)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.onSaveOrUpdate(DefaultSaveOrUpdateEventListener.java:70)
  at org.hibernate.impl.SessionImpl.fireSaveOrUpdate(SessionImpl.java:507)
  at org.hibernate.impl.SessionImpl.saveOrUpdate(SessionImpl.java:499)
  at org.hibernate.impl.SessionImpl.saveOrUpdate(SessionImpl.java:495)
  at com.foo.AbstractDao.saveOrUpdate(AbstractDao.java:29)
  at com.foo.LookupTableManager.addColumnToTable(LookupTableManager.java:338)
... etc ...
好的,我明白我得到的基本信息。但我不明白的是第二节课在哪里。。。。有人能帮我吗


我使用的是Hibernate 3.2.6.ga、Spring 2.5.5和Tomcat 6.0

我猜
lookupTableDao.findById
调用是在一个会话中获取对象,但是
lookupTableDao.save或Update
是另一个-如何通过Spring获取
会话
对象


对象来自何处-它已经在DB上了还是新的?

原来我根本没有事务。我在另一个配置文件中使用了几乎相同的事务配置

那里的切入点也被称为“管理者”,所以我的顾问在这里引用了另一个文件中的切入点


重命名切入点解决了我的问题。

问题在于视图中打开的会话筛选器映射。 它正在getSession上创建会话 另一个在保存

只能将singleSession更改为false
默认值为true

显然,使用merge可能会解决问题

myInstance = (myInstanceClass) Session.merge(myInstance);

如果您只想在代码的一部分上进行事务处理,可以使用如下方式:

import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
在课堂上:

@Autowired private SessionFactory sessionFactory;
稍后,围绕应在同一事务中执行操作的代码:

Session session = sessionFactory.openSession();
Transaction tx = session.beginTransaction();

Stuff stuff = getStuff();
manipulate(stuff);
send(stuff);
save(stuff);

tx.commit();

在一些长时间运行的批处理作业中,我在循环中使用了它。

我的以下代码也有同样的问题: 我想更新某个实体存储。我正在从该方法检索它:

@Override
public Store getStoreByStoreId(final long storeId) {
    getHibernateTemplate().execute(new HibernateCallback<Store>() {
        @Override
        public StoredoInHibernate(Session session) throws HibernateException, SQLException {
            return (Store) session.createCriteria(Store.class)
                    .add(Restrictions.eq(Store.PROP_ID, storeId))
                    .uniqueResult();
        }
    });
}
@覆盖
公共存储getStoreByStoreId(最终长存储ID){
getHibernateTemplate().execute(新的HibernateCallback()){
@凌驾
public StoredoInHibernate(会话会话)抛出HibernateeException、SQLException{
return(Store)session.createCriteria(Store.class)
.add(Restrictions.eq(Store.PROP_ID,storeId))
.uniqueResult();
}
});
}
然后,我用以下方法更新存储:

@Override
public void updateStoreByStoreId(final long storeId) {
    getHibernateTemplate().execute(new HibernateCallback<Void>() {
        @Override
        public Void doInHibernate(Session session) throws HibernateException, SQLException {
            Store toBeUpdated =  getStoreByStoreId(storeId);

            if (toBeUpdated != null){
                // ..change values for certain fields
                session.update(toBeUpdated);
            }
            return null;
        }
    });
} 
@覆盖
public void updatestrobystoreid(最终长存储ID){
getHibernateTemplate().execute(新的HibernateCallback()){
@凌驾
public Void doInHibernate(会话会话)抛出HibernateeException、SQLException{
Store toBeUpdated=getStoreByStoreId(storeId);
如果(toBeUpdated!=null){
//..更改某些字段的值
会话。更新(待更新);
}
返回null;
}
});
} 
事实证明,我得到了“非法尝试…”错误,因为get方法的第一个会话没有关闭,并且我正试图用另一个会话更新存储。我的解决方案是在update方法中移动检索要更新的存储的调用

@Override
public void updateStoreByStoreId(final long storeId) {
    getHibernateTemplate().execute(new HibernateCallback<Void>() {
        @Override
        public Void doInHibernate(Session session) throws HibernateException, SQLException {
            Store toBeUpdated =  (Store) session.createCriteria(Store.class)
                    .add(Restrictions.eq(Store.PROP_ID, storeId))
                    .uniqueResult();

            if (toBeUpdated != null){
                // ..change values for certain fields
                session.update(toBeUpdated );
            }
            return null;
        }
    });
} 
@覆盖
public void updatestrobystoreid(最终长存储ID){
getHibernateTemplate().execute(新的HibernateCallback()){
@凌驾
public Void doInHibernate(会话会话)抛出HibernateeException、SQLException{
Store toBeUpdated=(Store)session.createCriteria(Store.class)
.add(Restrictions.eq(Store.PROP_ID,storeId))
.uniqueResult();
如果(toBeUpdated!=null){
//..更改某些字段的值
会话。更新(待更新);
}
返回null;
}
});
} 

我使用的是windows server IIS,只是将AppPool管理的管道模式从集成更改为经典解决了我的问题


谢谢

[编辑,移动回复评论]:我通过org.springframework.orm.hibernate.support.HibernateDaoSupport的getSession()方法获取会话。这将从当前事务返回会话。。。列对象是新创建的。
@Override
public Store getStoreByStoreId(final long storeId) {
    getHibernateTemplate().execute(new HibernateCallback<Store>() {
        @Override
        public StoredoInHibernate(Session session) throws HibernateException, SQLException {
            return (Store) session.createCriteria(Store.class)
                    .add(Restrictions.eq(Store.PROP_ID, storeId))
                    .uniqueResult();
        }
    });
}
@Override
public void updateStoreByStoreId(final long storeId) {
    getHibernateTemplate().execute(new HibernateCallback<Void>() {
        @Override
        public Void doInHibernate(Session session) throws HibernateException, SQLException {
            Store toBeUpdated =  getStoreByStoreId(storeId);

            if (toBeUpdated != null){
                // ..change values for certain fields
                session.update(toBeUpdated);
            }
            return null;
        }
    });
} 
@Override
public void updateStoreByStoreId(final long storeId) {
    getHibernateTemplate().execute(new HibernateCallback<Void>() {
        @Override
        public Void doInHibernate(Session session) throws HibernateException, SQLException {
            Store toBeUpdated =  (Store) session.createCriteria(Store.class)
                    .add(Restrictions.eq(Store.PROP_ID, storeId))
                    .uniqueResult();

            if (toBeUpdated != null){
                // ..change values for certain fields
                session.update(toBeUpdated );
            }
            return null;
        }
    });
}