【问题标题】:Spring boot: JPA incorrectly adds where clauseSpring boot:JPA 错误地添加了 where 子句
【发布时间】:2018-02-11 13:49:50
【问题描述】:

我有三个实体类; StudentSubjectStudentSubject

StudentStudentSubject 上具有一对多关系,SubjectStudentSubject 上也具有一对多关系。

学生班

@Entity
@Getter
@Setter
public class Student {
    @Id
    private String email;

    @OneToMany(mappedBy = "student")
    @JsonManagedReference
    private List<StudentSubject> subjects;
    //more elements
}

学科类

@Entity
@Getter
@Setter
public class Subject {

    @Id
    @GeneratedValue
    private Long id;

    @ManyToOne
    @JsonBackReference
    private Teacher teacher;

    @OneToMany(mappedBy = "student")
    @JsonManagedReference
    private List<StudentSubject> students;
    //more elements
}

学生学科类

@Entity
@IdClass(StudentSubjectId.class)
@Getter
@Setter
public class StudentSubject implements Serializable {

    //Primary keys
    @Id
    @Column(name = "subject_id")
    Long subjectId;
    @Id
    @Column(name = "student_email")
    String studentEmail;

    String uid;

    @ManyToOne
    @JsonBackReference
    @JoinColumn(name = "subject_id", insertable = false, updatable = false)
    private Subject subject;
    @ManyToOne
    @JsonBackReference
    @JoinColumn(name = "student_email", insertable = false, updatable = false)
    private Student student;
}

我有 3 个班级,而不是 2 个班级,因为每个学生科目对都有特定的属性。因此有这样的安排。

当我从存储库中读取主题时,

Subject subject = subjectRepository.findByNameAndTeacher(subjectName, teacher);
subject.getStudents();

所有细节都是正确的,除了学生名单。它总是空的。(通过添加断点检查)


Hibernate/JPA 执行的查询是,

获取主题(?)

select
    subject0_.id as id1_3_,
    subject0_.name as name2_3_,
    subject0_.teacher_email as teacher_3_3_ 
from
    subject subject0_ 
    left outer join
        teacher teacher1_ 
        on subject0_.teacher_email = teacher1_.email 
where
    subject0_.name =? 
    and teacher1_.email =?

选择学生列表(?)

select
    students0_.student_email as student_1_2_0_,
    students0_.subject_id as subject_2_2_0_,
    students0_.student_email as student_1_2_1_,
    students0_.subject_id as subject_2_2_1_,
    students0_.uid as uid3_2_1_,
    subject1_.id as id1_3_2_,
    subject1_.name as name2_3_2_,
    subject1_.teacher_email as teacher_3_3_2_,
    teacher2_.email as email1_5_3_,
    teacher2_.name as name2_5_3_ 
from
    student_subject students0_ 
    left outer join
        subject subject1_ 
        on students0_.subject_id = subject1_.id 
    left outer join
        teacher teacher2_ 
        on subject1_.teacher_email = teacher2_.email 
where
    students0_.student_email =?

还有更多。

我认为这里的问题是最后一个 where 子句被错误地添加,并且表中的公共属性没有显示一次。我该如何解决这个问题?

【问题讨论】:

  • 您没有指定获取类型。将其设置为渴望

标签: java mysql spring hibernate spring-data-jpa


【解决方案1】:

您的映射有错字。在 Subject 类中,它应该是 @OneToMany(mappedBy = "subject") 而不是 mappedBy="student" 因此你的 where 子句是错误的。

这就是它使用的原因 where students0_.student_email =? 代替 where students0_.subject_id =? 因为它认为从主题中获取学生的方式是通过您的映射所示的 student_email 列。

【讨论】:

    【解决方案2】:

    您尚未指定提取类型。这应该解决它。

    @OneToMany(mappedBy = "student", fetch = FetchType.EAGER)
    @JsonManagedReference
    private List<StudentSubject> students;
    

    【讨论】:

    • 就这些了吗?正如你提到的,我在学生的学科课中添加了 fetchtype,但 hibernate 仍然使用 where 子句。
    • 添加fetch属性后是否会抓取学生?
    • 不,它没有。但是如果没有 where 子句,当我直接在 db 上尝试查询时它确实有效。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多