Issue
I encountered "Found shared references to a collection" error
but I have no idea how to fix it.
Is anyone who can give me some tips to solve it?
Thanks in advance.
Entity class(self join)
@Getter
@Setter
@EqualsAndHashCode(exclude={"operationData", "examDataList" })
@ToString(exclude={"operationData", "examDataList" })
@AllArgsConstructor
@NoArgsConstructor
@Entity
@Table(name = "IF_DATA")
public class IFData implements Serializable {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "IF_DATA_ID")
private Long ifDataId;
@Column(name = "BASE_YMD")
private String baseYmd;
@Column(name = "IF_ID")
private String ifId;
@Column(name = "PTNO")
private String ptno;
@Column(name = "JSON_DATA", columnDefinition = "json")
@Convert(converter = JsonConverter.class)
private JsonObject jsonData;
@Column(name = "DELETE_YN")
private String deleteYn;
@Column(name = "POST_IF_ID")
private String postIfId;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumns({@JoinColumn(name ="BASE_YMD", referencedColumnName = "BASE_YMD", insertable = false, updatable = false),
@JoinColumn(name ="PTNO", referencedColumnName = "PTNO", insertable = false, updatable = false),
@JoinColumn(name ="DELETE_YN", referencedColumnName = "DELETE_YN", insertable = false, updatable = false),
@JoinColumn(name ="IF_ID", referencedColumnName = "POST_IF_ID", insertable = false, updatable = false)})
private IFData operationData;
@OneToMany(mappedBy = "operationData", fetch = FetchType.LAZY, cascade = CascadeType.DETACH)
List<IFData> examDataList = new ArrayList<>();
}
Found shared references to a collection:examDataList" Error Occurs
But there is no same examDataList elements and examData in existingDataList
List<IFData> existingDataList = ifDataRepo.findByBaseYmdAndIfIdAndDeleteYnAndPtno(curYmd, ifDef.getServiceName(), Consts.YN_N, curJsonObj.get(Consts.PTNO).toString());
if (!CollectionUtils.isEmpty(existingDataList)) {
existingDataList.forEach(ifData -> {ifData.setDeleteYn(Consts.YN_Y);});
ifDataRepo.saveAllAndFlush(existingDataList);
}
Solution
The collection examDataList
is not a proper one-to-many association, but actually something ad-hoc, because for a proper association it is required that the FK columns point to a unique key. It seems the combination of the columns BASE_YMD, PTNO, DELETE_YN, IF_ID
is not unique though i.e. there are two IFData
objects with different IF_DATA_ID
, with the same values for BASE_YMD, PTNO, DELETE_YN, IF_ID
. Since the collection association is defined by the values for BASE_YMD, PTNO, DELETE_YN, IF_ID
, this means that you now have two distinct references for the same collection i.e. shared references.
This is illegal, because it's impossible to synchronize the object state with the database. You have to rethink your model.
If this really is an ad-hoc association, you should think about using a DTO projection for this and remove the @OneToMany
from your entity model.
Answered By - Christian Beikov
Answer Checked By - Candace Johnson (JavaFixing Volunteer)