Search code examples
hibernatejpaspring-data-jpamany-to-manysql-delete

Trying to delete/update child elements while keeping parent data


I have 3 tables in a chain, the top one being a 'Corridor' @Entity, the bottom being Segment @Entity, the middle being created via @JoinTable, with a ManyToMany relationship between the id columns in two other tables. This one is called CorridorSegments

I am trying to find a way to keep the corridor data, and delete all of the segments rows and corridor_segments rows that are in the database related to the corridor row. I then intend to replace them. So it's pretty much an update process, keeping the original data in the top 'corridor' table and linking it to new entries.

@Entity
@Table(name = "corridor")
@Cache(usage = CacheConcurrencyStrategy.NONSTRICT_READ_WRITE)
@Document(indexName = "corridor")
public class Corridor implements Serializable {

    private static final long serialVersionUID = 1L;

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    @NotNull
    @Column(name = "text_identifier", nullable = false)
    private String textIdentifier;

    @ManyToOne
    private Jurisdiction jurisdiction;
    //etc., etc., getters, setters, constructors, basic Entity class
}
@Entity
@Table(name = "segment")
@Cache(usage = CacheConcurrencyStrategy.NONSTRICT_READ_WRITE)
public class Segment {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    @NotNull
    @Column(name = "sequence", nullable = false)
    private Long sequence;


    @NotNull
    @Column(name = "name", nullable = false)
    private String name;
    //etc., etc., getters, setters, constructors, basic Entity class
}
@ManyToMany(cascade = {CascadeType.ALL}, fetch=FetchType.EAGER)
    @Cache(usage = CacheConcurrencyStrategy.NONSTRICT_READ_WRITE)
    @JoinTable(name = "corridor_segments",
        joinColumns = @JoinColumn(name="corridor_id", referencedColumnName="id"),
        inverseJoinColumns = @JoinColumn(name="segment_id", referencedColumnName="id"))
    private Set<Segment> segments = new HashSet<>();

I can save new entries to the segments table through my repository class that extends the JPARepository interface, using a simple segmentRepository.save(segment); But when I try to use the built in segmentRepository.delete();, it doesn't work.

I think it might be because I need to detach the relationships before the deletes will work, or change how that middle table is structured, but I'm not sure.

Any suggestions on how I can delete the data in the table and replace them? Thanks for all your help!


Solution

  • Load the Corridor for which you want to delete all Segment entries.

    From it iterate over the referenced Segment instances. For each on you need to remove it from all Corridor instances it is in. So it is no longer referenced. Then you can delete it using the delete operation on a SegementRepository.