Reputation: 4113
I'm very new to Spring and I'm trying to make a many-to-many relationship work as I expect. The relationships works fine, the tables are created and the data is inserted correctly. What I expect, is that when I empty a List (i.e. I empty the ArrayList "users" from an object of type "Group"), I expect the system to remove the relationships from the database - but it doesn't.
I have the following classes:
@Entity
@Table(name = "`group`")
public class Group
{
@Id
@GeneratedValue
@Column(name = "id")
private int id;
@Column(name = "name")
private String name;
@ManyToMany(cascade = {CascadeType.ALL})
@JoinTable(
name = "`user_has_group`",
joinColumns = @JoinColumn(name = "group_id", referencedColumnName = "id"),
inverseJoinColumns = @JoinColumn(name = "user_id", referencedColumnName = "id")
)
private List<User> users = new ArrayList<User>();
...
}
@Entity
@Table(name = "`user`")
public class User
{
@Id
@GeneratedValue
@Column(name = "id")
private int id;
@Column(name = "name")
private String name;
@ManyToMany(mappedBy = "users")
private List<Group> groups = new ArrayList<Group>();
...
}
Here are the DAOs:
@Repository
public class GroupJpaDao implements GroupDao
{
private EntityManager em;
@Transactional
public void save(Group group)
{
this.em.merge(group);
}
...
@PersistenceContext
void setEntityManager(EntityManager entityManager)
{
this.em = entityManager;
}
}
@Repository
public class UserJpaDao implements UserDao
{
private EntityManager em;
@Transactional
public void save(User user)
{
this.em.merge(user);
}
...
@PersistenceContext
void setEntityManager(EntityManager entityManager)
{
this.em = entityManager;
}
}
Here is the test method:
@Test
public void test()
{
Group g = new Group();
g.setName("Test group");
groupDao.save(g); // Works fine - inserts the group into the database
User u = new User();
u.setName("Test user");
userDao.save(u); // Works fine - inserts the user into the database
g.addUser(u);
groupDao.save(g); // Works fine - adds the many-to-many relationship into the database
g.removeAllUsers();
groupDao.save(g); // Doesn't work - I'm expecting it to remove all the related relationships from the database but it doesn't!
}
Am I doing something wrong or is it something not possible to do?
Any hint is really appreciated.
Thank you!
Upvotes: 7
Views: 5461
Reputation: 692151
I reread your question, and now the answer is clear. Your create a Group g
, and save it. But since your save method uses merge
, and you don't take into account the value returned by merge
to assign it to g
, you keep merging the transient group g, which never has any ID assigned. So, each time merge is called, you actually create a new group rather than modifying the previously created one.
Change the save method to
public Group save(Group group)
{
return this.em.merge(group);
}
and always reassign the result to g
:
g = groupDao.save(g);
Of course, the same must be done for the user.
Upvotes: 3
Reputation: 2777
you're only removing the users from the group, that's not enough. you need to remove all the users from the group and remove that group from all those users' list of groups.
Upvotes: 0