我有以下示例实体:
机构
@Data
@Entity
@NoArgsConstructor
@EntityListeners(InstitutionAuditListener.class)
public class Institution extends Auditable<String> {
@OneToMany(mappedBy = "institution", cascade = CascadeType.ALL)
@JsonManagedReference
private List<RegisteredProgram> registeredPrograms;
private String name;
}
注册程序
@Data
@NoArgsConstructor
@Entity
@EntityListeners(RegisteredProgramAuditListener.class)
public class RegisteredProgram extends Auditable<String> {
private String name;
@ManyToOne
@JoinColumn(name = "institution_id", nullable = false)
@JsonBackReference
private Institution institution;
@Embedded
private RegistrationRequirement registrationRequirement;
@OneToMany(mappedBy = "registeredProgram", cascade = CascadeType.ALL)
@JsonManagedReference
private List<Official> officialList;
}
官方的
@Data
@Entity
@EntityListeners(OfficialAuditListener.class)
@NoArgsConstructor
public class Official extends Auditable<String> {
private String name;
private String position;
@ManyToOne
@JoinColumn(name = "REGISTERED_PROGRAM_ID", nullable = false)
@JsonBackReference
private RegisteredProgram registeredProgram;
}
审核日志
@Entity
@Data
@NoArgsConstructor
public class AuditLog extends AuditBase {
@Id
@GeneratedValue(strategy = GenerationType.SEQUENCE)
private Long id;
private Long entityId;
@Type(type = "yes_no")
private Boolean isDeleted = false;
@Column(columnDefinition = "json")
@Convert(converter = JpaConverterJson.class)
private String jsonObject;
}
当我试图将official的object tostring()值的示例保存到auditlog的jsonobject字段中时,遇到以下错误:
java.lang.StackOverflowError: null
at java.base/java.lang.AbstractStringBuilder.ensureCapacityInternal(AbstractStringBuilder.java:173) ~[na:na]
at java.base/java.lang.AbstractStringBuilder.append(AbstractStringBuilder.java:538) ~[na:na]
at java.base/java.lang.StringBuilder.append(StringBuilder.java:174) ~[na:na]
at com.tesda8.region8.program.registration.model.entities.RegisteredProgram.toString(RegisteredProgram.java:26) ~[classes/:na]
at java.base/java.lang.String.valueOf(String.java:2951) ~[na:na]
at java.base/java.lang.StringBuilder.append(StringBuilder.java:168) ~[na:na]
at java.base/java.util.AbstractCollection.toString(AbstractCollection.java:473) ~[na:na]
at org.hibernate.collection.internal.PersistentBag.toString(PersistentBag.java:622) ~[hibernate-core-5.4.21.Final.jar:5.4.21.Final]
at java.base/java.lang.String.valueOf(String.java:2951) ~[na:na]
at java.base/java.lang.StringBuilder.append(StringBuilder.java:168) ~[na:na]
at com.tesda8.region8.program.registration.model.entities.Institution.toString(Institution.java:23) ~[classes/:na]
at java.base/java.lang.String.valueOf(String.java:2951) ~[na:na]
at java.base/java.lang.StringBuilder.append(StringBuilder.java:168) ~[na:na]
at com.tesda8.region8.program.registration.model.entities.RegisteredProgram.toString(RegisteredProgram.java:26) ~[classes/:na]
我想知道spring/hibernate中是否有任何注解可以阻止此问题的发生,或者是否有其他方法可以在spring中将对象的(json)值保存到对象的列中?我是这么想的 @JsonManagedReference
以及 @JsonBackReference
应该阻止这件事发生。
更新
我已经通过lombok的 @Data
注解
我也试着用 String.valueOf(official)
2条答案
按热度按时间bybem2ql1#
问题是你用的是Lombok山的
@Data
注解以生成equals
,hashCode
以及toString
方法。这将导致一些问题/奇怪之处(更多信息请参阅我写的这篇博文)。试着用Jackson
@JsonBackReference
当然不会解决toString
方法,这只对使用jackson库创建json有帮助。发生的是你的
toString
的Institution
会打电话给toString
的RegisteredProgram
. 这就叫toString
的Institution
再说一次,那就是toString
的RegisteredProgram
再说一遍(好吧,你可能明白了。不要依赖于
equals
,hashCode
以及toString
方法@Data
作为Lombok山的功能,正如在开始提到的,它将导致问题。你自己写吧equals
,hashCode
以及toString
或者至少声明哪些需要成为这些方法的一部分(最终结果甚至可能是手工编写这些方法更容易)。另一方面,不是存储
toString
一开始有点奇怪?相关链接
https://deinum.biz/2019-02-13-lombok-data-ojects-arent-entities/
https://vladmihalcea.com/how-to-implement-equals-and-hashcode-using-the-jpa-entity-identifier/
ddarikpa2#
为m干杯。戴纳姆对我问题的见解。https://stackoverflow.com/a/65388643/14806310
我的问题的根本原因确实是
toString()
由Lombok的@Data
将实体的详细信息保存到一个字段中,这是一个问题。我确实试过推翻toString()
方法RegisteredProgram
,解决了stackoverflow错误,但我保存json对象的方法仍然很奇怪。因此,与其将对象保存到
String
json列通过toString()
,我创建了一个新的hashmap字段entityAttributes
让我的实体持久化一个json对象。更新的审核日志实体
有关如何保存json对象的更多详细信息,请参见以下链接:https://www.baeldung.com/hibernate-persist-json-object
另外,向前看,我们确实建议您创建自己的
equals
,hashCode
以及toString
方法为您的实体和不依赖Lombok山等。