I'm building an API for the company where I work and it is my first time using Spring Boot, so I'm having some problems.
I have 2 classes, Compania (parent) and Office (Child). The class Compania has a OneToMany relationship with Office, and Office has a ManyToOne, and I'm struggling to find how could I add some children or edit one of them. Right now my classes are the following:
Compania (Parent)
@Entity(name = "Compania")
@Table(
name = "compania"
)
public class Compania {
@Id
@SequenceGenerator(
name = "compania_sequence",
sequenceName = "compania_sequence",
allocationSize = 1
)
@GeneratedValue(
strategy = GenerationType.SEQUENCE,
generator = "compania_sequence"
)
@Column(
nullable = false
)
private Long id;
@Column(
name = "name",
nullable = false,
unique = true
)
private String name;
@Column(
name = "dominio",
nullable = true
)
private String dominio;
@Column(
name = "altas"
)
private String altas;
@Column(
name = "bajas"
)
private String bajas;
@OneToMany(
mappedBy = "compania",
cascade = CascadeType.ALL,
fetch = FetchType.LAZY,
orphanRemoval = true
)
private List<Office> office;
...Constructors...
... Getters and Setters...
Office (Child)
@Entity()
@Table()
public class Office {
@Id
@SequenceGenerator(
name = "office_sequence",
sequenceName = "office_sequence",
allocationSize = 1
)
@GeneratedValue(
strategy = GenerationType.SEQUENCE,
generator = "office_sequence"
)
@Column(
nullable = false
)
@JsonIgnore
private Long id;
@Column(
name = "idRef",
nullable = false
)
private int idRef;
@Column(
name = "title",
nullable = false
)
private String title;
@Column(
name = "name"
)
private String name;
@Column(
name = "path"
)
private String path;
@ManyToOne(
fetch = FetchType.LAZY
)
@JoinColumn(
name = "compania_id",
referencedColumnName = "id"
)
private Compania compania;
...Constructors...
... Getters and Setters...
I would like to save data or edit it in my parent object (the one that has the OneToMany relationship) In order to achieve this, I thought of 2 methods but I have problems with both of them.
The first one would be saving everything in the Compania (Parent) class. Something like this, I pass the id of the Compania class and the JSON object as an Office object:
public void addOfficeTest(Long companiaId, Office office) {
// OPTION 1 - Add directly the office to the office list of the Compania Object (parent), then save it using Compania repository
if (office.getId() != null) {
office.setId(null);
}
Compania companiaFound = companiaRepository.findById(companiaId).get();
List<Office> listaOffice = companiaFound.getOffice();
listaOffice.add(office);
companiaFound.setOffice(listaOffice);
// method to set references id for user use...
setIdReferencia(companiaEnc, true, false);
companiaRepository.save(companiaEnc);
With this method, my problem is that is like I'm not being able to save my entities, when I make a GET to obtain my Companias I get the Office as an empty string. like this:
{
"id": 1,
"name": "Test Compania",
"dominio": "domain",
"altas": "OU=nn",
"bajas": "none",
"office": []
}
The other method I thought was this one, saving the Office with the Office repository, but that returned an infinite recursion error when I tried to fetch my Compania (as I'm saving the compania in office)...
public void addOfficeTest(Long companiaId, Office office) {
// OPTION 2 - Save Office with the repository office
if (office.getId() != null) {
office.setId(null);
}
Compania companiaEnc = companiaRepository.findById(companiaId).get();
office.setCompania(companiaEnc); // This causes recursion
officeRepository.save(office);
So I'm stuck here because I don't know how to do a PUT or a POST for my child objects. I don't know if something is wrong with my code or what. Maybe it has an easy solution, but I really can't find it. If someone could help giving me an example of how to do a POST and a PUT I would be very grateful...
Thanks
CodePudding user response:
Given that you have a bi-directional relationship I think you are missing setting the Compania
object in the new Office
. Something allong the following lines:
public void addOfficeTest(Long companiaId, Office office) {
// OPTION 1 - Add directly the office to the office list of the Compania Object (parent), then save it using Compania repository
if (office.getId() != null) {
office.setId(null);
}
Compania companiaFound = companiaRepository.findById(companiaId).get();
office.setCompania(companiaFound); // The new line
List<Office> listaOffice = companiaFound.getOffice();
listaOffice.add(office);
companiaFound.setOffice(listaOffice); // You actually don't need this because you've changed the List already
// method to set references id for user use...
setIdReferencia(companiaEnc, true, false);
companiaRepository.save(companiaEnc);
}