首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >添加@Transactional导致不再引用cascade=为“all-delete-orphan”的集合“

添加@Transactional导致不再引用cascade=为“all-delete-orphan”的集合“
EN

Stack Overflow用户
提问于 2013-06-15 07:27:50
回答 2查看 1.1K关注 0票数 0

我正在将一个工作项目从Spring2+Hibernate3升级到Spring3+Hibernate4。自从HibernateTemplate和HibernateDAOSupport退休后,我做了以下工作

之前(简化)

代码语言:javascript
复制
public List<Object> loadTable(final Class<?> cls)
{
    Session s = getSession(); // was calling the old Spring getSession
    Criteria c = s.createCriteria(cls);
    List<Object> objects = c.list();
    if (objects == null)
    {
        objects = new ArrayList<Object>();
    }
    closeSession(s);
    return objects;
}

现在(简化)

代码语言:javascript
复制
@Transactional(propagation=Propagation.REQUIRED)
public List<Object> loadTable(final Class<?> cls)
{
    Session s = sessionFactory.getCurrentSession();
    Criteria c = s.createCriteria(cls);
    List<Object> objects = c.list();
    if (objects == null)
    {
        objects = new ArrayList<Object>();
    }
    return objects;
}

我还向Spring XML添加了事务注释声明,并将其从Hibernate属性中删除

代码语言:javascript
复制
 "hibernate.current_session_context_class", "org.hibernate.context.ThreadLocalSessionContext"

正如我在堆栈跟踪中看到的那样,@Transactional注释似乎已经起到了作用

代码语言:javascript
复制
at com.database.spring.DatabaseDAOImpl$$EnhancerByCGLIB$$7d20ef95.loadTable(<generated>)

在初始化期间,上面概述的更改似乎适用于对loadTable函数的一些调用,但是当它加载一个具有父实体的实体时,我得到了“具有cascade=的集合”所有-删除-孤立“不再被引用”错误。由于我没有接触任何其他设置/获取父级或子级的代码,而只是尝试修复DAO方法,而查询只是执行sql SELECT,所以有人能看出代码为什么会出错吗?

这个问题似乎与Spring transaction management breaks hibernate cascade类似

EN

回答 2

Stack Overflow用户

发布于 2013-06-15 16:58:00

这不太可能是Spring的问题,而是实体处理/定义的问题。当您在关系上使用deleteOrphans时,不能从实体本身中移除底层的PersistentSet 。您只能修改set实例本身。所以,如果你想在你的实体setter中做任何聪明的事情,那就是原因。

此外,据我所知,当你在关系的两端都有deleteOrphans和/或在一个会话中加载/操作两端时,会有一些问题。

顺便说一句。我不认为"hibernate.current_session_context_class", "org.hibernate.context.ThreadLocalSessionContext"是必要的。在我们的项目中,这是我们唯一的配置:

代码语言:javascript
复制
@Bean
public LocalSessionFactoryBuilder sessionFactoryBuilder() {
    return ((LocalSessionFactoryBuilder) new LocalSessionFactoryBuilder(
            dataSourceConfig.dataSource()).scanPackages(ENTITY_PACKAGES).
            setProperty("hibernate.id.new_generator_mappings", "true").
            setProperty("hibernate.dialect", dataSourceConfig.dialect()).
            setProperty("javax.persistence.validation.mode", "none"));
}

@Bean
public SessionFactory sessionFactory() {
    return sessionFactoryBuilder().buildSessionFactory();
}
票数 0
EN

Stack Overflow用户

发布于 2013-06-26 06:16:38

问题出在会话管理上。正在进行自己的会话处理的其他模块正在调用相同的事务性代码块。雪上加霜的是,一些调用模块是Spring bean,而另一些则是用直接Hibernate API风格编写的。这种杂乱无章的工作足以阻止我们立即升级到Hibernate 4。

教训(你喜欢这个英语吗?):在整个项目中使用一致的DAO实现,并坚持明确定义的会话和事务管理策略。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/17118688

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档