当前位置: 首页 > 面试题库 >

在JPA或Hibernate中更新ManyToMany关系

谈桐
2023-03-14
问题内容

Entity下面有两个…

@Entity
@Table(name = "USER")
public class User {
    @Id
    private Long id;

    private String name;

    @ManyToMany(fetch = FetchType.LAZY, mappedBy = "groupMemberList")
    @Fetch(FetchMode.SELECT)
    private List<Group> groupList = new ArrayList<>();

    // Getters - Setters
}


@Entity
@Table(name = "GROUP")
public class Group {
    @Id
    private Long id;

    private String name;

    @ManyToMany(fetch = FetchType.LAZY/*, mappedBy = "groupList"*/)
    @Fetch(FetchMode.SELECT)
    @JoinTable(name = "SEC_GROUP_VS_MEMBER", joinColumns = @JoinColumn(name = "GROUP_ID"),
            inverseJoinColumns = @JoinColumn(name = "MEMBER_ID"))
    private List<User> groupMemberList;

    // Getters - Setters
}

我想更新的User,有时也Group用下面的方法有时…

方法#1

public boolean updateGroup(Long groupId, List<Staff> groupMemberList) {
    Group group = hibernateTemplate.get(Group.class, groupId);

    group.setGroupMemberList(groupMemberList);
    hibernateTemplate.merge(group); // Group updated with the users
    return true;
}

方法#2

public boolean updateUser(Long userId, List<Group> groupList) {
    User user = hibernateTemplate.get(User.class, userId);

    user.setGroupList(groupList);
    hibernateTemplate.merge(user); // User not updated with the groups
    return true;
}

第一种方法可以正常工作,但第二种则不能。但是,当我将“ join table从” Group.class移至“
User.class第二”方法时,效果很好,而不是第一个。


问题答案:

问题是一个Owning Entity问题。

假设它Staff是的子类User,那么您的问题是关系中只有一方是拥有实体。将mappedBy = "groupMemberList"使得Group实体所属的实体,因此仅改变该实体被持久化。这意味着,你必须更新groupMemberListGroup这两种情况下的实体。如果您有一个“
a”的组列表,User则必须遍历该组列表并将其添加User到其中。该groupListUser仅用于检索。

给定UserGroupMember实体:

@Entity
public class User {
    @Id @GeneratedValue
    private Long id;

    @ManyToMany(mappedBy = "groupMemberList")
    private List<GroupMember> groupList;

@Entity
public class GroupMember {
    @Id @GeneratedValue
    private Long id;

    @ManyToMany
    private List<User> groupMemberList;

然后:

// create starting user and membergroup    
tx.begin();
User user = new User();
em.persist(user);
GroupMember group = new GroupMember();
em.persist(group);
tx.commit();
em.clear();

// update users for groupId 2
System.out.println("update users for groupId 2");
tx.begin();
List<User> users = new ArrayList<>();
users.add(user);
group.setGroupMemberList(users);
em.merge(group);            
tx.commit();
em.clear();

// update groups for userId 1 -- doesn't work, not owner of relationship
System.out.println("update groups for userId 1 -- doesn't work, not owner of relationship");
tx.begin();
List<GroupMember> groups = new ArrayList<>();
groups.add(group);
user.setGroupList(groups);
em.merge(user);            
tx.commit();
em.clear();

// update groups for userId 1 -- works
System.out.println("update groups for userId 1 -- works");
tx.begin();
for ( GroupMember groupMember: groups) {
    groupMember.getGroupMemberList().add(user);
    em.merge(groupMember);            
}
tx.commit();
em.clear();

提供以下SQL输出:

Hibernate: insert into User (id) values (?)
Hibernate: insert into GroupMember (id) values (?)
update users for groupId 2
Hibernate: select groupmembe0_.id as id1_0_0_ from GroupMember groupmembe0_ where groupmembe0_.id=?
Hibernate: select groupmembe0_.groupList_id as groupLis1_1_0_, groupmembe0_.groupMemberList_id as groupMem2_1_0_, user1_.id as id1_4_1_ from GroupMember_User groupmembe0_ inner join User user1_ on groupmembe0_.groupMemberList_id=user1_.id where groupmembe0_.groupList_id=?
Hibernate: select user0_.id as id1_4_0_ from User user0_ where user0_.id=?
Hibernate: insert into GroupMember_User (groupList_id, groupMemberList_id) values (?, ?)
update groups for userId 1 -- doesn't work, not owner of relationship
Hibernate: select user0_.id as id1_4_0_ from User user0_ where user0_.id=?
Hibernate: select groupmembe0_.id as id1_0_0_ from GroupMember groupmembe0_ where groupmembe0_.id=?
update groups for userId 1 -- works
Hibernate: select groupmembe0_.id as id1_0_0_ from GroupMember groupmembe0_ where groupmembe0_.id=?
Hibernate: select groupmembe0_.groupList_id as groupLis1_1_0_, groupmembe0_.groupMemberList_id as groupMem2_1_0_, user1_.id as id1_4_1_ from GroupMember_User groupmembe0_ inner join User user1_ on groupmembe0_.groupMemberList_id=user1_.id where groupmembe0_.groupList_id=?
Hibernate: delete from GroupMember_User where groupList_id=?
Hibernate: insert into GroupMember_User (groupList_id, groupMemberList_id) values (?, ?)
Hibernate: insert into GroupMember_User (groupList_id, groupMemberList_id) values (?, ?)


 类似资料:
  • 我正在将项目的数据库管理从JDBC MySQL转换为JPA Hibernate,数据库应该保持不变。(从一个简单的Jersey API到带有Hibernate API的spring)。 有公司表、客户表和优惠券表。每个公司可以管理许多优惠券,每个客户也可以‘购买’许多优惠券。 因此,我有一个名为company_coupon的联接表和另一个名为customer_coupon的表。 当删除一个公司时,

  • 我在数据表和通过data_user表链接的用户表之间有一个Hibernate ManyToMany映射。现在我想更新数据表,以便在数据中再添加一个用户。如何更新链接表(data_user)为新用户添加一个条目? NonUniqueObjectException:一个具有相同标识符值的不同对象已经与会话相关联。 PS:我对冬眠很陌生。

  • 为了使问题变得简单,让我们假设我有一个具有三个属性的用户实体:id、email和一组角色(owner、@manytomany、@jointable)。我将合并至少具有一个或多个角色用户实体,而不通过EntityManager查找它: 数据库中的结果是:

  • 我试图存储一个manytomany关系,但它没有存储关系。 下面的代码生成了3个表。 这是我发送到服务器的JSON: {“abbreviatedsequence”:“xdf”,“medals”:[{“name”:“purple”,“id”:1},{“name”:“red”,“id”:2}],“sequence”:“xdfree”,“name”:“savier”} java

  • 和 和 我的存储库:

  • 问题内容: 我想知道是否有人对这些框架的JPA2.0实现有经验?特别是与带有EclipseLink支持的Spring3.x一起使用。 您是否使用任何这些框架和JPA2.0进行生产?有什么 严重的 问题吗? 问题答案: 恕我直言,总是尽可能使用标准的api。您自己的示例完美地展示了这一点。当一个提供商无法按预期工作时,您可以在两个提供商上尝试使用相同的代码。切换到任何本机API都会阻止您执行此操作。