拨开荷叶行,寻梦已然成。仙女莲花里,翩翩白鹭情。
IMG-LOGO
主页 文章列表 问:事务代码为什么这幺好用?

问:事务代码为什么这幺好用?

白鹭 - 2022-03-25 1962 0 0

你好,我的专业人士我有一个简单的问题,我想乞求解决这个问题..

这是成员的物体

@Entity
@Getter
@Builder
@NoArgsConstructor(access = AccessLevel.PROTECTED)
@AllArgsConstructor
/*@ToString(of = {"id", "username", "age"})*/
public class Member {

    @Id
    /*@GeneratedValue(strategy = GenerationType.IDENTITY)*/
    @Column(name = "member_id")
    private Long id;

    private String username;

    private int age;

    @OneToMany(fetch = FetchType.LAZY, cascade = CascadeType.ALL, mappedBy = "member")
    private List<Team> teams;

    @OneToMany(fetch = FetchType.LAZY, cascade = CascadeType.ALL,  mappedBy = "member")
    private List<Coach> coachs;

}

这是教练的物体

@Entity
@AllArgsConstructor
@Getter
@Builder
@Setter
@NoArgsConstructor
@ToString(of = {"id","name","career"})
public class Coach {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name= "coach_id")
    private Long id;

    @Column
    private String name;

    @Column
    private String career;

    @ManyToOne(fetch = FetchType.LAZY,cascade = ALL)
    @JoinColumn(name = "member_id")
    private Member member;

    @OneToOne(fetch = FetchType.LAZY,cascade = ALL)
    @JoinColumn(name = "team_id")
    private Team team;

}

这是控制器代码

    @GetMapping("/member")
public void createUser(){
     Member m = memberService.createMember();
     Coach c = m.getCoachs().get(0);
     log.info(c.getName());
}

这是服务代码

private final MemberRepository memberRepository;

    @Transactional
    public Member createMember(){
        return memberRepository.findMemberById(3L);
    }

最后一个是 RepositoryCode

Member findMemberById(Long id);

所以我的问题是,当我在控制台上的控制器上打印出教练的名字时

它打印得很好。

但我知道事务已从服务结束所以持久性容器已关闭,这意味着无法汇入教练名称,因为它的延迟加载和持久性容器已关闭,但打印得很好

我想知道为什么...

这是控制台结果谢谢!

[2022-01-10 23:27:46.835] [http-nio-9000-exec-2] [] INFO  o.a.c.c.C.[.[.[/] - Initializing Spring DispatcherServlet 'dispatcherServlet' 
[2022-01-10 23:27:46.835] [http-nio-9000-exec-2] [] INFO  o.s.w.s.DispatcherServlet - Initializing Servlet 'dispatcherServlet' 
[2022-01-10 23:27:46.855] [http-nio-9000-exec-2] [] INFO  o.s.w.s.DispatcherServlet - Completed initialization in 19 ms 
Hibernate: 
    /* select
        generatedAlias0 
    from
        Member as generatedAlias0 
    where
        generatedAlias0.id=:param0 */ select
            member0_.member_id as member_i1_1_,
            member0_.age as age2_1_,
            member0_.username as username3_1_ 
        from
            member member0_ 
        where
            member0_.member_id=?
[2022-01-10 23:27:47.007] [http-nio-9000-exec-2] [4c0222d3] INFO  p6spy - #1641824867007 | took 15ms | statement | connection 1| url jdbc:mariadb://patrick-lab.cjeq2ffynlc2.ap-northeast-2.rds.amazonaws.com:3306/patricklab?characterEncoding=UTF-8&serverTimezone=UTC
/* select generatedAlias0 from Member as generatedAlias0 where generatedAlias0.id=:param0 */ select member0_.member_id as member_i1_1_, member0_.age as age2_1_, member0_.username as username3_1_ from member member0_ where member0_.member_id=?
/* select generatedAlias0 from Member as generatedAlias0 where generatedAlias0.id=:param0 */ select member0_.member_id as member_i1_1_, member0_.age as age2_1_, member0_.username as username3_1_ from member member0_ where member0_.member_id=3; 
[2022-01-10 23:27:47.170] [http-nio-9000-exec-2] [4c0222d3] INFO  p6spy - #1641824867170 | took 12ms | commit | connection 1| url jdbc:mariadb://patrick-lab.cjeq2ffynlc2.ap-northeast-2.rds.amazonaws.com:3306/patricklab?characterEncoding=UTF-8&serverTimezone=UTC

; 
Hibernate: 
    select
        coachs0_.member_id as member_i4_0_0_,
        coachs0_.coach_id as coach_id1_0_0_,
        coachs0_.coach_id as coach_id1_0_1_,
        coachs0_.career as career2_0_1_,
        coachs0_.member_id as member_i4_0_1_,
        coachs0_.name as name3_0_1_,
        coachs0_.team_id as team_id5_0_1_ 
    from
        coach coachs0_ 
    where
        coachs0_.member_id=?
[2022-01-10 23:27:47.200] [http-nio-9000-exec-2] [4c0222d3] INFO  p6spy - #1641824867200 | took 12ms | statement | connection 1| url jdbc:mariadb://patrick-lab.cjeq2ffynlc2.ap-northeast-2.rds.amazonaws.com:3306/patricklab?characterEncoding=UTF-8&serverTimezone=UTC
select coachs0_.member_id as member_i4_0_0_, coachs0_.coach_id as coach_id1_0_0_, coachs0_.coach_id as coach_id1_0_1_, coachs0_.career as career2_0_1_, coachs0_.member_id as member_i4_0_1_, coachs0_.name as name3_0_1_, coachs0_.team_id as team_id5_0_1_ from coach coachs0_ where coachs0_.member_id=?
select coachs0_.member_id as member_i4_0_0_, coachs0_.coach_id as coach_id1_0_0_, coachs0_.coach_id as coach_id1_0_1_, coachs0_.career as career2_0_1_, coachs0_.member_id as member_i4_0_1_, coachs0_.name as name3_0_1_, coachs0_.team_id as team_id5_0_1_ from coach coachs0_ where coachs0_.member_id=3; 
[2022-01-10 23:27:47.213] [http-nio-9000-exec-2] [4c0222d3] INFO  m.p.l.m.c.MemberController - Coach1 

uj5u.com热心网友回复:

我相信这是因为您使用的spring.jpa.open-in-view是设定为 true的 spring-boot 默认设定

此属性启用OpenSessionInView模式,您可以简单地认为在处理任何 HTTP 请求时(例如,在 Servlet 过滤器等中),事务将在开始时自动为您打开。因此,在您的服务方法执行之前,事务实际上已经打开,并且在您的服务方法完成后它仍然处于活动状态。因此,LazyInitializationException即使您在服务方法之外访问未初始化的属性,您也不会遇到任何问题,因为事务仍然处于活动状态。

关于 spring-boot 过去是否应该默认启用它存在激烈的争论。如果您有兴趣,可以参考此内容以获取更多详细信息。我个人建议关闭它。

uj5u.com热心网友回复:

事务仅意味着您正在数据库中的物理事务块内执行一组操作。它不会关闭持久性背景关系。

另一方面,延迟加载与事务无关。延迟加载意味着hibernate在加载父级时实际上并没有加载所有子级。相反,它会在请求时加载它们。你可以明确地请求这个,或者,这是更常见的,当你尝试访问一个孩子时,hibernate会自动加载它们。

在您的情况下,教练不是由Member m = memberService.createMember();加载的,而是由 m.getCoachs()

标签:

0 评论

发表评论

您的电子邮件地址不会被公开。 必填的字段已做标记 *