[英]JPA: Selecting entities based on multiple criterions on multiple child entities
[英]Collecting all child entities from multiple different entities
我有 3 个实体 A、B 和 C。
数据库方面有 5 个表。 各个实体的 3 个表和 2 个单独的链接表,一个包含 A 和 C 之间的链接(A_to_C),另一个包含 B 和 C 之间的链接(B_to_C)。 在我的存储库中,我试图从特定的 A 记录中检索所有 C 实体,这意味着来自 A 本身的 C 实体和通过 B 链接的 C 实体。
在传统的 SQL 中,这可以使用以下方法完成:
select C.*
from A
left join A_to_C on A_to_C.A_ID = A.ID
left join B_to_C on B_to_C.B_ID = A.B_ID
inner join C on C.ID = A_to_C.C_ID OR C.ID = B_to_C.C_ID
where A.ID = '1';
或(从 C 开始)
select C.*
from C
left join A_to_C on A_to_C.C_ID = C.ID
left join B_to_C on B_to_C.C_ID = C.ID
inner join A on A.B_ID = B_to_C.B_ID OR
A.ID = A_to_C.A_ID
where A.ID = '1';
在这些 SQL 示例中没有指向 B 的表的链接,因为 A 包含 B 的 ID,它也是 B_to_C 中使用的 ID,所以我真的不需要它。 我也知道这些并不完全相同,但是当我只对 C 感兴趣时它们会产生相同的结果。
不过,我真的很想知道如何在 CriteriaBuilder(最好)或 JPQL 中执行此操作。 我对 jpa 还是比较陌生,所以我希望这里有人可以帮助我。
我相信,即使有机会在vanilla JPQL上取得成功,您也需要通过添加@ManyToOne
方将关联转换为双向关联(或单向多对一)。 然后您可以从C
开始查询。 @OneToMany
端,如果你想保留它,在这种情况下成为关联的反面,但是:
@Entity
public class C {
@ManyToOne
@JoinTable
private B b;
@ManyToOne
@JoinTable
private A a;
}
@Entity
public class B {
@ManyToOne
@JoinTable
private A a;
@OneToMany(mappedBy = "b")
private List<C> cs;
}
@Entity
public class A {
@OneToMany(mappedBy = "a")
private List<B> bs;
@OneToMany(mappedBy = "a")
private List<C> cs;
}
一旦你这样做了,JPQL 查询就会变成这样:
SELECT c FROM C c
LEFT JOIN c.a a
LEFT JOIN c.b b
LEFT JOIN b.a a2
WHERE a.id = :id OR a2.id = :id
如果您不同意将关联的“一侧”设为反面,那么您就不走运了。 最简单的解决方案是使用本机查询。
Eclipselink JPQL 扩展包含一个ON
子句,所以也许您可以将ON
与MEMBER OF
结合使用:
SELECT c FROM C c
LEFT JOIN A a ON c MEMBER OF a.cs
LEFT JOIN B b ON c MEMBER OF b.cs
LEFT JOIN A a2 ON b MEMBER OF a2.cs
WHERE a.id = :id OR a2.id = :id
不过,我非常怀疑它会起作用,即使它起作用,我也会警惕生成的 SQL,因为它可能不是最理想的。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.