首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >静默忽略remove()

静默忽略remove()
EN

Stack Overflow用户
提问于 2016-01-17 16:53:28
回答 2查看 2.7K关注 0票数 4

有实体A指(多对一)实体B,有从B到A的反向(映射)引用,还有引用A到C和反向引用C到A。当我发布entityManager.remove(A)然后刷新()时,“删除”没有关联!但也没有例外。这就像根本没有调用remove()一样。为什么会发生这种事?如果在删除()之前,我们从反向引用B.listOfA和C.listOfA中提取A,则会按预期生成"delete“。

还请注意my another question,在这里我得出的结论是,orphanRemoval并不总是像预期的那样工作。现在,我开始怀疑,级联可能运行良好,但之后,实际的级联清除被“吞咽”,如我在这里描述。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2016-01-17 20:37:51

看看这个answer。基本上,JPA规范要求,如果将持久化操作应用于被删除的实体,将再次对其进行管理。

要验证是否真的发生了这种情况,请为org.hibernate包启用跟踪日志级别,并搜索日志条目,如:

代码语言:javascript
复制
un-scheduling entity deletion ...

为了避免任何不可预测的行为,建议从加载同一会话/事务的所有其他实体实例中删除对已删除实体的引用。

票数 10
EN

Stack Overflow用户

发布于 2020-05-16 18:19:42

我有这个问题。即使启用了show_sql:

代码语言:javascript
复制
<property name="hibernate.show_sql" value="true"></property>

没有输出,删除命令被静默忽略。

这个问题是围绕着一个OneToMany关系的: todo 1-* todoitem

环境是:- JSF 18 (JPA默认实现- Hibernate) - PostgreSQL 10

尝试删除任何一方的实例都会以静默方式失败,而服务器的输出没有相应的“删除”命令,也没有任何类型的异常消息。

溶液

首先,我从以下几个方面切换了Wildfly18 18/JBoss文档在其示例中建议的多个方面的代码:

代码语言:javascript
复制
//    @Override
//    public void delete(Todoitem todoitem) {
//        if (todoitem == null) {
//            return;
//        }
//        if (!emPg.contains(todoitem)) {
//            todoitem = emPg.merge(todoitem);
//        }
//        emPg.remove(todoitem);
//        emPg.flush();
//        emPg.clear();
//    }

以同等形式:

代码语言:javascript
复制
@Override
public void delete(Todoitem todoitem) {
    if (todoitem == null) {
        return;
    }
    Todoitem ti = emPg.find(Todoitem.class, todoitem.getId());
    if(ti == null) {
        return;
    }
    emPg.remove(ti);
    emPg.flush();
    emPg.clear();
}

不幸的是,我得到了同样的结果-删除默默无闻。

然后,我怀疑数据库,因为hibernate处理自己的密钥。我在实现过程中做了很多测试.为了确保一致性问题,我决定清空数据库,删除关系双方的内容。然后,我使用应用程序的资源(没有SQL命令)创建了新的实体实例和关系,因为除了实体删除之外,一切都运行良好。之后,我使用SQL命令检查了数据库关系,以确保一切正常。

接下来,我又试了一次新的测试,但这次是成功的。

然后,我返回代码,取消注释的代码,反之亦然,并再次测试。测试再次失败,返回相同的结果--默默地忽略删除。

我再次将代码设置为以前的条件测试,以确认结果。确认成功,证实了对数据库和代码实现这两个问题的怀疑。

由于好消息,我在" one“方面重复了同样的话(下面的代码--注释代码是从Wildfly 18文档继承的初始代码,如前所述)。

发自:

代码语言:javascript
复制
//    @Override
//    public void delete(Todo todo) {
//        if(todo == null) {
//            return;
//        }
//        if (!emPg.contains(todo)) {
//            todo = emPg.merge(todo);
//        }
//        //todoitemDao.deleteAll(todo);
//        emPg.remove(todo);
//        emPg.flush();
//    }

至:

代码语言:javascript
复制
@Override
public void delete(Todo todo) {
    if (todo == null) {
        return;
    }
    Todo t = emPg.find(Todo.class, todo.getId());
    if(t == null) {
        return;
    }
    emPg.remove(t);
    emPg.flush();
    emPg.clear();
}

再次重复测试,但这次不删除Todoitem实例(“多”侧),而是删除Todo实例("one“侧)。

问题解决了。成功。

重要注意事项:

直接在数据库上使用SQL语句检查删除测试。有时,由于缓存问题或代码实现错误,实例似乎没有被删除,需要分开处理。

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

https://stackoverflow.com/questions/34840903

复制
相关文章

相似问题

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