Siema, może ktoś będzie w stanie mi pomóc ogarnąć magię JPA. Mam dwie encje: Customer i YogaClass które chciałbym połączyć relacją many to many:
@Entity
@Table(name = "customer")
@Data
public class Customer {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String name;
private String lastName;
@OneToMany
private Set<Pass> passes;
@ManyToMany(cascade = CascadeType.ALL)
@JoinTable(
name = "customer_yoga_class",
joinColumns = { @JoinColumn(name = "customer_id", referencedColumnName="id") },
inverseJoinColumns = { @JoinColumn(name = "yoga_class_id", referencedColumnName="id") }
)
@JsonIgnoreProperties(value = "attendees")
private Set<YogaClass> yogaClasses;
}
@Entity
@Table(name = "yoga_class")
@Data
public class YogaClass {
@Id
@GeneratedValue
private Long id;
private String instructor;
private LocalDateTime date;
private Integer spotsLeft;
@ManyToMany(mappedBy = "yogaClasses")
@JsonIgnoreProperties(value = "yogaClasses")
@Nullable
private Set<Customer> attendees;
}
Zapisuje po jednym Customer
i YogaClass
w bazie danych, następnie chce przypisać jedno do drugiego w ten sposób:
public void addAttendee(String custId, String classId) {
YogaClass classToUpdate = yogaClassRepository.findById(Long.parseLong(classId))
.orElseThrow(EntityNotFoundException::new);
Customer customerToAdd = customerService.findById(Long.parseLong(custId))
.orElseThrow(EntityNotFoundException::new);
classToUpdate.getAttendees().add(customerToAdd);
classToUpdate.setSpotsLeft(classToUpdate.getSpotsLeft() - 1);
customerToAdd.getYogaClasses().add(classToUpdate);
yogaClassRepository.save(classToUpdate);
customerService.put(customerToAdd);
}
Niestety podczas wykonywania metody addAttendee leci stackOverflowError:
java.lang.StackOverflowError: null
at org.hibernate.collection.spi.PersistentSet.hashCode(PersistentSet.java:410) ~[hibernate-core-6.5.2.Final.jar:6.5.2.Final]
at io.github.project_yoga.domain.yogaclass.YogaClass.hashCode(YogaClass.java:14) ~[classes/:na]
at java.base/java.util.AbstractSet.hashCode(AbstractSet.java:124) ~[na:na]
at org.hibernate.collection.spi.PersistentSet.hashCode(PersistentSet.java:410) ~[hibernate-core-6.5.2.Final.jar:6.5.2.Final]
Czytałem trochę o circular reference w JPA, ale nie pomagają żadne @JsonManagedReference
, @JsonBackReference
czy inne rozwiazania. Próbowałem to ograć również w taki sposób: https://vladmihalcea.com/the-best-way-to-map-a-many-to-many-association-with-extra-columns-when-using-jpa-and-hibernate/ ale efekt był ten sam. Jestem w szoku że z pozoru tak prosta rzecz dostarcza tylu problemów. Ktoś ma pomysł jak to ugryźć?