Reputation: 7581
When deleting the parent of children (in a 1 to many unidirectional relation) I keep on getting these errors. When I delete the children first, everything works OK.
I don't need/want a bi-directional relationship.
This is the parent:
@Entity
@Table(name = "datagroup")
public class DataGroup implements java.io.Serializable {
@Id
@Column(name = "group_id", unique = true, nullable = false)
private int group_id;
private String name;
@OneToMany( targetEntity=DataGroupItem.class, fetch=FetchType.LAZY, cascade = CascadeType.REMOVE)
@JoinColumn(name="group_id")
private List<DataGroupItem> dataGroupItems = new ArrayList<>( 0);
... setters and getters
}
And this is the child:
@Entity
@Table(name = "datagroupitems")
public class DataGroupItem implements java.io.Serializable {
@Id
@Column(name = "item_id", nullable = false)
private int item_id;
private String name;
@Column(name = "group_id", nullable = false)
private int group_id = 0; // only for (un)delete
... getters and setters
}
When deleting the parent in a Controller I do:
@RestController
@RequestMapping("/learner/groups")
public class LearnerSyncServices {
@Autowired
private IDataGroupRepository dataGroupRepository;
@Autowired
private IDataGroupItemRepository dataGroupItemRepository;
...
@RequestMapping( method= RequestMethod.DELETE, value="/{id}")
public void delete(@PathVariable String id) {
try {
int idx = Integer.parseInt( id);
dataGroupRepository.delete( idx);
} catch (Exception e) {
logger.error( "Cannot delete " + id + " " + e.getMessage());
}
}
As JPA version I have: Spring boot version 4.1.3.
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
Deleting the group with at least 1 child gives the following messages:
.. WARN org.hibernate.engine.jdbc.spi.SqlExceptionHelper - SQL Error: 1048, SQLState: 23000
.. ERROR org.hibernate.engine.jdbc.spi.SqlExceptionHelper - Column 'group_id' cannot be null
.. INFO org.hibernate.engine.jdbc.batch.internal.AbstractBatchImpl - HHH000010: On release of batch it still contained JDBC statements
.. ERROR nl.deholtmans.tjm1706.learner.LearnerSyncServices - Cannot delete 101 could not execute statement; SQL [n/a]; constraint [null]; nested exception is org.hibernate.exception.ConstraintViolationException: could not execute statement
Upvotes: 1
Views: 2042
Reputation: 10716
When deleting the DataGroup
, hibernate first tries to issue the SQL statement that will delete the parent, and then proceeds to issue statements that remove the children.
When deleting the parent, the foreign key in the datagroupitems
table must be set to NULL
to maintain db consistency (at that point, it is not obvious to the db that children rows are going to be deleted as well). However, it cannot be set to NULL
because you specifically forbade it in your schema definition.
Hibernate simply does not know it should delete children first, parent last. You can fix this by allowing the group_id
column to be nullable.
EDIT If you're not using 'hbm2ddl.auto/javax.persistence.schema-generation.database.action', do not forget to recreate/manually update your db schema. The NOT NULL
constraint needs to be dropped from the database for this solution to work.
Upvotes: 1