当前位置: 首页 > 知识库问答 >
问题:

spring数据存储库不删除多个实体

缪坚诚
2023-03-14

我目前正在尝试使用spring数据存储库删除我的一些实体。delete调用工作时没有任何异常/错误消息,但之后不会删除实体。

这些是我的实体:

public class Board implements Serializable {

    @Id
    @GeneratedValue(generator = "uuid2")
    @GenericGenerator(name = "uuid2", strategy = "uuid2")
    @Column(columnDefinition = "BINARY(16)")
    private UUID uuid;

    @OneToMany(fetch=FetchType.EAGER, cascade=CascadeType.ALL, orphanRemoval = true, mappedBy = "board")
    private List<Post> posts = new ArrayList<Post>();
}

而且

public class Post implements Serializable {

    @Id
    @GeneratedValue
    private long id;

    @ManyToOne(optional = false)
    @JoinColumn(name="board_uuid", updatable = false, nullable = false)
    @JsonBackReference
    private Board board;
}

存储库非常简单:

@Repository
public interface PostRepository extends CrudRepository<Post, Long> {
}

delete调用类似于

postRepository.delete(50);

有什么想法为什么这个变化没有反映在数据库中吗?

编辑1:

我找到了变通办法,但我还是不明白真正的问题是什么。如果我像这样删除帖子(有几个例外,因为违反了约束,但帖子仍然会被删除),它就“起作用”了:

post.setBoard(null);
postRepo.delete(post);

编辑2:

当我查看执行的SQL语句时,我可以看到hibernate甚至没有尝试删除。唯一会发生的是这两个select语句:

Hibernate: select post0_.id as id1_1_0_, post0_.board_uuid as board_uu6_1_0_, post0_.content as content2_1_0_, post0_.x as x3_1_0_, post0_.y as y4_1_0_, post0_.z as z5_1_0_, board1_.uuid as uuid1_0_1_ from Post post0_ left outer join Board board1_ on post0_.board_uuid=board1_.uuid where post0_.id=?
Hibernate: select posts0_.board_uuid as board_uu6_0_0_, posts0_.id as id1_1_0_, posts0_.id as id1_1_1_, posts0_.board_uuid as board_uu6_1_1_, posts0_.content as content2_1_1_, posts0_.x as x3_1_1_, posts0_.y as y4_1_1_, posts0_.z as z5_1_1_ from Post posts0_ where posts0_.board_uuid=?

编辑3

结果发现cascade=cascadeType.posts上的所有内容似乎都是问题所在。没有它,delete可以正常工作(但我现在错过了对帖子的级联更改)

共有2个答案

仉洲
2023-03-14

基于上面user2936091的出色回答,我只想提到我今天偶然发现的一个(相关的)解决方法:如果父实体没有被提取到Hibernate上下文中,您可以直接删除它。

在我的示例中,这是通过在@ManyToOne关系上设置fetch=fetchType.lazy来实现的。由于性能原因,我希望进行此更改,并且注意到,没有急切地获取的父级,Hibernate可以自由地通过存储库方法调用删除它。

颜阳炎
2023-03-14

问题似乎是您使用的是cascade=cascadeType.all,其中还包括cascadeType.persistcascadetype.persist表示子实体完全由父实体管理,您不能直接删除它。为了删除,您只需要从父级中删除它。

您可以只添加其他cascadeTypes而不是全部。例如cascadetype.remove,如果您只想在删除父级时删除子级。

 类似资料:
  • 我在使用JPA时遇到了一些困难。我没有得到任何异常,但我不能保存任何东西到数据库。我从Hibernate到Jpa,在那里一切都工作得很好。下面是我的文件 Application.Properties: 存储库: 服务: 我在提交表单时得到了200的响应,但在数据库中找不到数据

  • 问题内容: 解决此问题的最佳做法是什么?有内置的批处理功能吗? 样例代码: 提前致谢。 问题答案: HQL支持IN子句,如果使用setParameterList,甚至可以传递一个集合。 请注意,就像ddango在评论中提到的那样,将不会执行在对象中指定的关系级联,因为运行HQL查询只是转换为DB查询,并且实际上不会加载任何实体对象。

  • 我读到删除分离的实体将导致IllegalArgumentExcetpion,该实体应该被管理删除。但是,我使用的是spring JPA存储库接口,删除操作是对一个分离的实体进行的,我已经用我想要删除的ID创建了新的实体,我没有例外。在spring jpa中是否有文档说明我们可以删除分离的实体?我找不到正式文件。

  • 我有两个bean配置。每个数据库都指向具有不同模式的单独数据库(一个是Oracle,另一个是内存中的H2) 我可以做什么来解决每个存储库应该使用什么Entitymanager的模糊性?现在我得到了这个错误: 我想我可以提供一个快速的解决方法,只需使用类似 我给你一个当前场景的想法: spring-config:有两个EM 从这里开始的所有内容都在“package com.foo.repos.ora

  • 我想使用Spring LDAP 设置多个 LDAP 存储库。我的目标是同时在所有存储库中创建或更新对象。 我使用LdapRepository Spring接口,我认为目前这是不可能的。 我想知道我是否可以创建自己的LdapRepository来扩展Spring,但是我不知道如何开始。 这是我的配置: 完整地说,一个存储库: 知道怎么做吗? 提前感谢任何帮助。

  • 主要内容:所需步骤,示例代码在本教程将演示如何在JDBC应用程序中删除一个指定的数据库。 在执行以下示例之前,请确保您已经准备好以下操作: 具有数据库管理员权限,以在给定模式中创建数据库。 要执行以下示例,需要用实际用户名和密码替换这里用户名()和密码()。 MySQL或数据库已启动并运行。 注意:这是一个严肃的操作,在继续删除数据库之前必须要确定是否真的执行删除操作,因为删除了数据库以后,数据库中的所有内容都将丢失,并且无