我有一个开发项目,使用SpringDataJPA和MapStruct在实体和DTO之间进行映射。上周我决定是时候解决FetchType.EAGER
vsLAZY
问题了,我已经推迟了一段时间。我选择使用@NamedEntityGraph
和@EntityGraph
在需要时加载属性。但是,在执行从实体到dto的映射时,我遇到了这个问题。我想我知道这在哪里发生,但我不知道如何通过它。
密码
@NamedEntityGraph(name="Employee.full", ...)
@Entity
public class Employee {
private Set<Role> roles = new HashSet<>();
}
@Entity
public class Role {
private Set<Employee> employees = new HashSet<>();
}
public interface EmployeeRepository extends JpaRepository<Employee, Long> {
@EntityGraph(value = "Employee.full")
@Override
Page<Employee> findAll(Pageable pageable);
}
@Service
public class EmployeeService {
public Page<EmployeeDTO> findAll(PageRequest pageRequest) {
Page<Employee> employees = repository.findAll(pageRequest); // ok
Page<EmployeeDTO> dtos = employees.map(emp -> mapper.toDTO(emp, new CycleAvoidMappingContext()); // this is where the exception happens
return dtos;
}
}
// also there is EmployeeDTO and RoleDTO classes mirroring the entity classes
// and there is a simple interface EmployeeMapper loaded as a spring component
// without any special mappings. However CycleAvoidingMappingContext is used.
我已经跟踪了当映射器试图映射角色依赖关系时发生的Lazy初始化异常
。Role
对象有Set
使用
中,这不再有效。FetchType时。EAGER
new CycleAvoidingMappingContext()
解决了这个问题,但是在LAZY
有人知道如何避免异常,同时正确映射我的DTO吗?
问题在于,当代码从findAll
返回时,实体不再被管理。因此,您有一个LazyInitializationException
,因为您正在会话范围之外尝试访问尚未初始化的集合。
添加渴望使其工作,因为它确保集合已经初始化。
你有两个选择:
EAGER
fetch;findAll
. Adding a @Transactional
to the method should work: @Service
public class EmployeeService {
@Transactional
public Page<EmployeeDTO> findAll(PageRequest pageRequest) {
Page<Employee> employees = repository.findAll(pageRequest);
Page<EmployeeDTO> dtos = employees.map(emp -> mapper.toDTO(emp, new CycleAvoidMappingContext());
return dtos;
}
}
我想说,如果您需要初始化集合,那么急切地获取它(使用实体图或查询)是有意义的。
有关Hibernate ORM中实体状态的更多详细信息,请查看本文。
更新:发生此错误的原因似乎是Mapstruct
正在转换集合,即使DTO中不需要它。在这种情况下,您有不同的选项:
roles
from the DTO. Mapstruct will ignore the field in the entity because the DTO doesn't have a field with the same name;roles
;@Mapping
annotation to ignore the field in the entity: @Mapping(target = "roles", ignore = true)
void toDTO(...)
@Mapping(target = "roles", ignore = true)
void toSkipRolesDTO(...) // same signature as toDTO
我已经在其他项目中多次遇到这个问题。现在我试图理解异常处理,但我仍然不知道它到底是如何工作的。我试图用循环编程一个计算器,当我试图输入字符串时,会出现InputMismatchException-我试图捕捉它,但出于某种原因,在catch子句之后,java给了我另一个InputMismatchException,为什么? 起初有一个无限循环,我用扫描器求解。nextInt() 在catch块内,但
问题内容: 我有以下代码片段。 上面的代码用于生成5个链接,并将每个链接与警报事件绑定以显示当前链接ID。但这是行不通的。当您单击生成的链接时,它们都说“链接5”。 但是以下代码段符合我们的预期。 这里引用了以上两个片段。 但是它是如何工作的以及 关闭 是如何工作的,这些都是我无法理解的。为什么第一个不起作用而第二个却起作用?任何人都可以对魔术进行详细说明吗? 谢谢。 问题答案: 解释第一个示例:
我是java的新手,我正在编写这个简短的程序,您可以在其中猜测1到10之间的数字。正确的数字存储为整数。如果您猜测较低的数字,它应该说“正确的数字较高”,如果您猜测较高,它应该说“正确的数字较低”。这是我所拥有的: 所以很明显这是行不通的,因为如果你输入一个更小的数字,它会跳到下一个数字,即使这个数字更大,它也是正确的。那么,我如何解决这个问题,让它检查两个语句呢?抱歉解释得不好。谢了。
我已经创建了一个字符串数组,其中包含单词“磅”、“美元”和“欧元”,我想把这些标签放在旗帜的左边(为了用户应用程序的清晰性,因为不是每个用户都知道哪个货币属于哪个国家)。 我创建了一个循环,将创建一个标签,并将其分配到旗帜的左侧,它应该使一个"英镑"标签,然后一个"美元",然后一个"欧元"每次穿越Y轴南部,使他们与旗帜对齐然后,它将重置数组计数以返回到正确的字符串,沿着x轴移动并再次重复。然而,它
本文向大家介绍spring循环注入异常问题的解决方案,包括了spring循环注入异常问题的解决方案的使用技巧和注意事项,需要的朋友参考一下 今天在做项目的时候突然遇到一个问题:启动服务器的时候spring没报错,可是当我访问某个页面的时候spring报Request bean is currently in creation: is there an unresolvable circular r
这段代码是为一个基本的杂货计算器的按钮。当我按下按钮时,一个输入对话框显示您在哪里输入您的商品价格。我遇到的问题是,我不知道如何获得循环,使输入对话框在输入后弹出。 我希望它总是回来,除非用户选择ok与nothing或cancel,在这种情况下,循环应该中断并填充剩余的框。使用当前的代码,我必须每次手动按下按钮来恢复对话框。我一直在玩不同的while条件和if语句,但我似乎无法让它发挥作用。我是一