В моем тестовом классе Spring я пытаюсь заполнить свою базу данных методом @BeforeAll.
@BeforeAll
static void beforeAll(@Autowired TeamRepository teamRepository,
@Autowired StudentRepository studentRepository) {
teams = new ArrayList<>();
students = new ArrayList<>();
final int nTeams = 20;
IntStream.range(0, nTeams)
.forEach(i -> {
Team team = Team.builder()
.name("team-"+i)
.status(TeamStatus.ACTIVE)
.members(new ArrayList<>())
.build();
teams.add(team);
teamRepository.save(team);
IntStream.range(0, 3)
.forEach(k -> {
Student student = Student.builder()
.id("s" + k + "-" + i)
.name("name-" + k + "-" + i)
.firstName("first_name-" + k + "-" + i)
.teams(new ArrayList<>())
.build();
team.addStudent(student);
students.add(student);
studentRepository.save(student);
});
});
}
Связь между двумя объектами - @ ManyToMany.
Student.java
@Entity
@Data
@EqualsAndHashCode(onlyExplicitlyIncluded = true)
@AllArgsConstructor
@NoArgsConstructor
@Builder
public class Student {
@Id
@EqualsAndHashCode.Include
String id;
String name;
String firstName;
@ManyToMany(mappedBy = "members", cascade = {CascadeType.PERSIST, CascadeType.MERGE})
List<Team> teams = new ArrayList<>();
public void addTeam(Team team) {
teams.add(team);
team.members.add(this);
}
public void removeTeam(Team team) {
teams.remove(team);
team.members.remove(this);
}
}
Team.java
@Data
@Entity
@EqualsAndHashCode(onlyExplicitlyIncluded = true)
@AllArgsConstructor
@NoArgsConstructor
@Builder
public class Team {
@Id
@GeneratedValue
@EqualsAndHashCode.Include
Long id;
String name;
TeamStatus status;
@ManyToMany(cascade = {CascadeType.PERSIST, CascadeType.MERGE})
@JoinTable(name = "team_student",
joinColumns = @JoinColumn(name = "team_id"),
inverseJoinColumns = @JoinColumn(name = "student_id")
)
List<Student> members = new ArrayList<>();
public void addStudent(Student student) {
members.add(student);
student.teams.add(this);
}
public void removeStudent(Student student) {
members.remove(student);
student.teams.remove(this);
}
}
С этим кодом Hibernate будет сохранять дубликаты, как показано на изображениях ниже. Единственное решение, которое я нашел, - не вызывать studentRepository.save()
и сохранять team
только в конце. Причина, по которой я публикую этот вопрос, заключается в том, что я пытаюсь понять, почему это происходит и почему количество дубликатов различается для разных объектов.
Пример:
введите описание изображения здесь