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

Spring Data JPA-删除子实体而不是在更新时设置为null?

冀萧迟
2023-03-14
users
----
id (PK)
name

orders
------
id (PK)
userid (PK)
name

在使用JPA更新用户时,如果我尝试使用

User user = userRepository.getOne(id);
user.getOrders().clear();
userRepository.save(user);

JPA首先尝试将关联订单上的userid设置为null,然后删除该行。这将失败,因为userid是不可为空的,并且是主键的一部分。有没有一种方法可以告诉JPA它只需要删除Order行,而不首先将userid列设置为null?

映射:我有的映射是这样的:

@Entity
@Table(name = "users")
public class User implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name="id")
    public Long id;

    @Column(name="name")
    private String name;

    @OneToMany(cascade = CascadeType.ALL, orphanRemoval = true)
    @JoinColumn(name="userid", referencedColumnName = "id", insertable = true, updatable = true)
    @Fetch(FetchMode.JOIN)
    private Set<Order> orders;

}

@Entity
@Table(name = "orders")
@IdClass(Order.OrderPk.class)
public class Order implements Serializable {

    @Id
    @Column(name="id")
    private Long id;

    @Id
    @Column(name="userid")
    private Long userId;

    @Column(name="name")
    private String name;

    public static class OrderPk implements Serializable  {

        private Long id;

        private Long userId;
    }
}
@Entity
@Table(name = "users")
public class User implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name="id", nullable = false)
    public Long id;

    @Column(name="name")
    private String name;

    @OneToMany(cascade = CascadeType.ALL, orphanRemoval = true, fetch = FetchType.EAGER, mappedBy = "orderPk.user")
    @Fetch(FetchMode.JOIN)
    private Set<Order> orders;
}

@Entity
@Table(name = "orders")
public class Order implements Serializable {

    @EmbeddedId
    private OrderPk orderPk;

    @Column(name="name")
    private String name;

    @Embeddable
    public static class OrderPk implements Serializable {

        @GeneratedValue
        @Column(name="id", insertable = false, updatable = false, nullable = false)
        private Long id;

        @ManyToOne(fetch = FetchType.LAZY)
        @JoinColumn(name="userid", referencedColumnName = "id", insertable = false, updatable = false, nullable = false)
        private User user;
    }
}

共有1个答案

仲孙兴平
2023-03-14

您可以使用标识符保留联接,并确保delete不会尝试使用集合上的可更新和可插入注释将null写入集合FK。

@Entity
@Table(name = "users")
public class User implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name="id", nullable = false)
    public Long id;

    @Column(name="name")
    private String name;

    @OneToMany(cascade = CascadeType.ALL, orphanRemoval = true, fetch =     FetchType.EAGER)
    @JoinColumn(name = "userId", updatable = false, insertable = false)
    private Set<Order> orders;
}

@Entity
@Table(name = "orders")
public class Order implements Serializable {

    @Id
    @Column(name="id")
    private Long id;

    @Column(name="userid")
    private Long userId;

    @Column(name="name")
    private String name;
}

这个

@joincolumn(name=“userid”,updatable=false,insertable=false)

 类似资料:
  • 删除父实体时,我还想删除关联的子实体(从数据库中)。我试图在删除时使用级联,如下所示,但我一定做错了什么。 当对父实体对象调用删除时,我收到错误消息:“该实体仍在数据库的其他地方引用”。我可以确认该实体在数据库的其他地方引用的唯一地方是在下面的两个表中(如果我手动从数据库中删除子行,对父实体对象的删除调用工作正常)。在过去的9个小时里,我一直在阅读实体对象并尝试不同的东西。我做错了什么? 这是我的

  • 我的实体更新有问题。如你所见,我有三个实体。 包含类中的列表。 包含类中的列表。 从我的SQL语句中可以看到,字段和是唯一的。我的表中只允许该组合的一行。 当我用类的新列表更新父实体()时,我希望Hibernate删除旧列表本身并创建新实体。一个一个地更新孩子是有点困难的。这就是为什么我要直接删除所有相关的孩子。 当我更新并为其提供包含具有唯一名称的和(数据库中已存在的实体)组合的列表时,我会出现

  • 注意:如果我只有一个孩子,我可以删除它,没有任何例外,如果我有2个或更多的孩子,我有一个例外。 谢谢你的帮助!

  • 我的实体。ValidationStep与documentDetail有一对一的关系,documentDetail与documentValidations有一个完全的关系 我的删除查询 父ValidationStep被删除,但是docDetail和documentValidations仍然在数据库中。

  • 在这种情况下,我希望检索数据,但在返回数据之前,我希望在不保存/持久化的情况下对其进行更改。 这是我的Rest控制器: 以下是服务实现: 最初我在服务上有注释。通过删除它而不在方法中使用它,我首先想到的是会话将使用存储库打开和关闭,如这里的答案所示。 这不起作用,我在评论中看到“会话将持续整个HTTP请求处理过程。”所以,在我添加的服务中 然后在我添加的方法中 在我做任何改变之前。然而,我所做的任

  • 问题内容: 如果我从父表中删除一条记录,我希望子表中的相应记录被删除。 如何从子表中删除Hibernate,而不是尝试使用null更新? 我正在使用Hibernate 3,但目前无法使用注释。我在下面附上了HBM,DAO等的副本。 - 先感谢您 尝试从父子关系中的表中删除数据时,出现以下错误: 我的表是: 家长 : 儿童: HBM XML 道 问题答案: 我遇到这个错误 所有 的时间。 只需在关系