【发布时间】:2022-10-05 01:44:47
【问题描述】:
我在下面有三个 Hibernate @Entity,它们模仿了我的生产应用程序中的失败:
@Entity
@Data
@SuperBuilder(toBuilder = true)
@EqualsAndHashCode(callSuper = true)
@NoArgsConstructor
@AllArgsConstructor
public class Dog extends Animal {
String barkType;
}
Dog 实体对此类 Animal 使用 JOINED 继承:
@Entity
@Inheritance(strategy = InheritanceType.JOINED)
@Data
@SuperBuilder(toBuilder = true)
@NoArgsConstructor
@AllArgsConstructor
public class Animal {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@Type(type = "uuid-char")
private UUID id;
@OneToMany(cascade = CascadeType.REMOVE)
@JoinColumn(name = "animalId", referencedColumnName = "id", insertable = false, updatable = false)
@Builder.Default
private List<Toy> toys = new ArrayList<>();
}
这个Toy实体与父类相关,Animal
@Entity
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class Toy {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@Type(type = "uuid-char")
private UUID id;
@Type(type = "uuid-char")
private UUID animalId;
private String shape;
}
这是我正在测试的实现:
@Service
@AllArgsConstructor
public class DogService {
DogRepository repository;
ToyRepository toyRepository;
@Transactional
public Dog saveDogDTO(DogDTO dogDTO) {
Dog entity = Dog.builder()
.barkType(dogDTO.getBarkType())
.build();
repository.save(entity);
toyRepository.save(Toy.builder()
.shape(dogDTO.getToyShape())
.animalId(entity.getId())
.build());
return entity;
}
}
这是我失败的测试,在最后一行失败:
@DataJpaTest
class DogServiceTests {
private DogService dogService;
@Autowired
private DogRepository dogRepository;
@Autowired
private ToyRepository toyRepository;
@Test
void save_not_working_example() {
dogService = new DogService(dogRepository, toyRepository);
var dogDTO = DogDTO.builder()
.barkType("big bark")
.toyShape("some shape")
.build();
var savedDog = dogService.saveDogDTO(dogDTO);
assertThat(dogRepository.count()).isEqualTo(1);
assertThat(toyRepository.count()).isEqualTo(1);
var findByIdResult = dogRepository.findById(savedDog.getId());
assertThat(findByIdResult.get().getToys()).hasSize(1);
}
}
测试失败消息:
Expected size: 1 but was: 0 in:
[]
java.lang.AssertionError:
Expected size: 1 but was: 0 in:
[]
问题似乎是双 JPA 存储库在 @Transaction 中保存冲突。有没有办法克服这个问题?我尝试将@Transactional(propagation = Propagation.NEVER) 添加到测试中,但后来我得到了这个失败:
failed to lazily initialize a collection of role: com.example.datajpatest.demo.models.Animal.toys, could not initialize proxy - no Session
org.hibernate.LazyInitializationException: failed to lazily initialize a collection of role: com.example.datajpatest.demo.models.Animal.toys, could not initialize proxy - no Session
【问题讨论】:
-
dog Repository.count() 和 toy Repository.count() 实际上在做什么?
标签: spring-boot hibernate spring-data-jpa data-jpa-test