无法在一对多映射中删除子项并添加新子项 [Hibernate]

huangapple 未分类评论50阅读模式
英文:

Unable to remove childs in OneToMany Mapping and add new childs [Hibernate]

问题

我知道这个问题已经被问过很多次,但是没有一个解决方案适用于我。

所以我有一个父类:

class User{

@Id
@NotNull
@Column(name = "UserId", nullable = false)
private Long userId;

@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER, orphanRemoval = true)
@JoinColumn(name = "UserId")
private Set<Phone> phoneList;
}

还有一个子类:

class Phone {
@ManyToOne(fetch = FetchType.EAGER)
@JoinColumn(name = "UserId")
private User user;
}

现在当我收到一个更新用户类的新手机列表时,我想要删除所有旧的手机并添加新的手机。请注意,所有这些操作都发生在同一个 @Transactional 中。

我尝试过的解决方案:

user.getPhoneList().clear();   
user.getPhoneList().addAll(新的手机列表);

当我尝试上述逻辑时,Hibernate 试图将旧的手机的 userId 设置为 null。在这个位置上,我得到一个 DataIntegrityViolation,因为 Phone 表中的 userId 是非空列。

请提供一个适当的解决方案,可以在这里工作。

英文:

I know this question has been asked many times but none of the solution is working for me.

So I have a Parent class :

class User{

@Id
@NotNull
@Column(name = &quot;`UserId`&quot;, nullable = false)
private Long userId;

@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER, orphanRemoval = true)
@JoinColumn(name = &quot;`UserId`&quot;)
private Set&lt;Phone&gt; phoneList;
}

And a child class:

class Phone {
@ManyToOne(fetch = FetchType.EAGER)
@JoinColumn(name = &quot;`UserId`&quot;)
private User user;
}

Now when I received a update for User class with new phone list, I want to remove all the old phones and add new phones. Please note that this all operation is happening in same @Transactional.

Solution I tried:

user.getPhoneList().clear()
user.getPhoneList().addAll(new phone list)

When I try the above logic, Hibernate is trying to set old phone with userId as null. At this position I am getting DataIntegrityViolation as userId in Phone table is non null column.

Please provide any appropriate solution which can work here.

答案1

得分: 0

Hhhmmm... 我有完全相同的逻辑而且我的代码能正常运行这是我的类

@Data
@Entity
public class ProductReference {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private long id;

    @OneToMany(mappedBy = "productReference", fetch = FetchType.EAGER, cascade = CascadeType.REMOVE, orphanRemoval = true)
    private Set<Attribute> attributes = new HashSet<>();

}

唯一我看到的区别是 `CascadeType.REMOVE`:

@Data
@Entity
public class Attribute {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private long id;

    @ManyToOne
    private ProductReference productReference;
}

我的删除操作

productReference.getAttributes().clear();

你使用的 Hibernate 版本是多少我使用的是 `org.hibernate.Version - HHH000412: Hibernate Core {5.4.10.Final}`
英文:

Hhhmmm... I have the exact same logic and it works fine by me. Here are my classes

@Data
@Entity
public class ProductReference {

@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private long id;


@OneToMany(mappedBy = &quot;productReference&quot;, fetch = FetchType.EAGER, cascade = CascadeType.REMOVE, orphanRemoval = true)
private Set&lt;Attribute&gt; attributes = new HashSet&lt;&gt;();

}

The only difference I see is the CascadeType.REMOVE

@Data
@Entity
public class Attribute {

@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private long id;

@ManyToOne
private ProductReference productReference;
}

My deletion:

productReference.getAttributes().clear();

Which Hibernate version you have? by me it is org.hibernate.Version - HHH000412: Hibernate Core {5.4.10.Final}

huangapple
  • 本文由 发表于 2020年7月24日 14:48:20
  • 转载请务必保留本文链接:https://java.coder-hub.com/63068266.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定