是否可以 JPA/Hibernate 仅对父字段使用 ManyToOne?
Is it possible JPA/Hibernate use ManyToOne with only parent field?
我尝试在我的 Menus 实体之间建立只有一个字段的关系:Parent
我这样做是这样的:
@Entity
@Table
@Getter @Setter
public class ProductCategory extends BaseEntity {
@Column
private String name;
@Column
private String description;
@ManyToOne
@JoinColumn(name = "PARENT_ID")
private ProductCategory parent;
}
但我遇到了 直接自引用导致循环 错误。是否可以只使用一个字段来建立关系?或者我必须将 child 字段定义为 JsonManagedReference?
我用@OneToMany 做了一次同样的事情,如下所示:
@Entity
@Data
@NoArgsConstructor
@Table(name = "categories")
public class Category {
@JsonProperty("Id")
@Id
private int id;
@JsonProperty("Code")
private String code;
@JsonProperty("Name")
private String name;
@JsonProperty("ParentId")
@Column(name = "parent_id")
private Integer parent;
@JsonProperty("NewAdminId")
private int newAdminId;
@JsonProperty("VolumetricWeight")
@Column(name = "volumetricWeight")
private Float volumetricWeight = 0.0f;
@JsonProperty("Nodes")
@OneToMany(
cascade = CascadeType.ALL,
fetch = FetchType.EAGER,
orphanRemoval = true)
@JoinColumn(name = "parent_id")
private List<Category> categories;
public Category(int id, String code, String name, int newAdminId, List<Category> categories) {
this.id = id;
this.code = code;
this.name = name;
this.newAdminId = newAdminId;
this.categories = categories;
}
}
证明有效的测试:
@RunWith(SpringRunner.class)
@DataJpaTest
public class CategoryRepositoryTests {
@Autowired
private TestEntityManager entityManager;
@Autowired
private CategoryRepository categoryRepository;
@Test
public void when_findAll_with_specification_returnTopCategory() {
Category topRoot = CategoryBuilder.aCategory()
.code("1")
.id(1)
.name("test root category")
.newAdminId(1)
.parent(null)
.build();
Category child = CategoryBuilder.aCategory()
.code("2")
.id(2)
.name("test child category")
.newAdminId(2)
.parent(1)
.build();
entityManager.persistAndFlush(topRoot);
entityManager.persistAndFlush(child);
List<Category> found = categoryRepository.findAll(isTopRoot());
assertThat(found).hasSize(1);
assertThat(found.get(0)).isEqualTo(topRoot);
}
}
我尝试在我的 Menus 实体之间建立只有一个字段的关系:Parent
我这样做是这样的:
@Entity
@Table
@Getter @Setter
public class ProductCategory extends BaseEntity {
@Column
private String name;
@Column
private String description;
@ManyToOne
@JoinColumn(name = "PARENT_ID")
private ProductCategory parent;
}
但我遇到了 直接自引用导致循环 错误。是否可以只使用一个字段来建立关系?或者我必须将 child 字段定义为 JsonManagedReference?
我用@OneToMany 做了一次同样的事情,如下所示:
@Entity
@Data
@NoArgsConstructor
@Table(name = "categories")
public class Category {
@JsonProperty("Id")
@Id
private int id;
@JsonProperty("Code")
private String code;
@JsonProperty("Name")
private String name;
@JsonProperty("ParentId")
@Column(name = "parent_id")
private Integer parent;
@JsonProperty("NewAdminId")
private int newAdminId;
@JsonProperty("VolumetricWeight")
@Column(name = "volumetricWeight")
private Float volumetricWeight = 0.0f;
@JsonProperty("Nodes")
@OneToMany(
cascade = CascadeType.ALL,
fetch = FetchType.EAGER,
orphanRemoval = true)
@JoinColumn(name = "parent_id")
private List<Category> categories;
public Category(int id, String code, String name, int newAdminId, List<Category> categories) {
this.id = id;
this.code = code;
this.name = name;
this.newAdminId = newAdminId;
this.categories = categories;
}
}
证明有效的测试:
@RunWith(SpringRunner.class)
@DataJpaTest
public class CategoryRepositoryTests {
@Autowired
private TestEntityManager entityManager;
@Autowired
private CategoryRepository categoryRepository;
@Test
public void when_findAll_with_specification_returnTopCategory() {
Category topRoot = CategoryBuilder.aCategory()
.code("1")
.id(1)
.name("test root category")
.newAdminId(1)
.parent(null)
.build();
Category child = CategoryBuilder.aCategory()
.code("2")
.id(2)
.name("test child category")
.newAdminId(2)
.parent(1)
.build();
entityManager.persistAndFlush(topRoot);
entityManager.persistAndFlush(child);
List<Category> found = categoryRepository.findAll(isTopRoot());
assertThat(found).hasSize(1);
assertThat(found.get(0)).isEqualTo(topRoot);
}
}