【问题标题】:LazyInitialization exception on ManyToOne relationshipManyToOne 关系上的 LazyInitialization 异常
【发布时间】:2021-12-17 18:09:49
【问题描述】:

我在使用 spring 时遇到了延迟初始化异常。我知道这是一个常见错误,并且我已经解决了几个堆栈问题,但没有一个答案真的对我有用。这是我的场景:我有两个这样相关的类:

public class Foo implements Serializable {
    @Id
    @EqualsAndHashCode.Include
    @Column(name = "uuid")
    private UUID uuid;

    @Column(name = “attribute”)
    private String attribute;

    @OneToMany(fetch = FetchType.LAZY, mappedBy = “foo”)
    private Set<Bar> bar;
}

public class Bar implements Serializable {

    @Id
    @Column(name = "uuid")
    private UUID uuid;

    @ManyToOne(fetch = FetchType.LAZY)
    @JoinColumn(name = “foo_uuid")
    private Foo foo;
}

我有一个列出所有 Bar 对象的休息端点。在那个特定的端点中,我需要返回 attribute,它是一个 Foo 属性。由于在应用程序业务逻辑中不需要这样做,因此似乎也没有必要将 attribute 添加到 Bar 中。所以我有一个BarWrapper类,它是Bar的自定义格式,由端点返回:

@Getter
@Setter
@NoArgsConstructor
public class BarWrapper {
    …
    private String attribute;

    public BarWrapper(final Bar bar) {
        //The next line throws lazy initialization exception.
        this.attribute = bar.getFoo().getAttribute()

}

我在所有课程上都尝试过@Transactional,但没有奏效。我尝试添加cascade = CascadeType.ALL,这确实有效,但不是一个好习惯。我也尝试为此创建一个自定义函数,但也没有帮助:

@Transactional
    private String extractAttribute(final Bar bar){
        final Foo foo = bar.getFoo();
        return foo.getAttribute();
    }

如何克服这个延迟初始化异常?

编辑:

这就是我调用 BarWrapper 构造函数的方式:

@AllArgsConstructor
@Service
@Slf4j
public class BarApplicationServices {


private final FooService fooService;
private final BarService barService;


public BarWrapper createBar(final CreateBarRequestBody requestBody) {
    final Foo foo = fooService.findFooToBeSettled(requestBody.getFooUuid());
    final Bar createdBar = barService
            .createBar(new Bar(foo));
    return new BarWrapper(createdBar);
}


}

【问题讨论】:

  • BarWrapper的构造函数怎么调用?向我们展示那里的代码,它应该在 Service 方法中,您可以在该方法中从数据库中加载 Bar 实体,以确保调用 bar.getFoo() 将在同一个事务中。
  • 你为什么在 Bar 类中懒惰地初始化 Foo 对象?
  • @memoricab 这是一个相当大的对象,我实际上并不经常使用。
  • @pleft 按要求添加了代码。
  • 但是如果你懒惰地获取那个对象,你就看不到它的内容,对吧?那么当您尝试访问尚未获取的内容时,它会引发异常,这不是很正常吗?

标签: java spring spring-boot jpa java-11


【解决方案1】:

您的@Transactional 方法是private,它不起作用。设为public

如果这不起作用,请尝试以下link

【讨论】:

  • 嗨,亚瑟。改变对公众的可见性并没有帮助。我会进一步查看您发送的链接。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-02-13
  • 2011-03-30
  • 1970-01-01
  • 2013-08-20
相关资源
最近更新 更多