含复合主键表的过滤与关联查询:Spring Data JPA实现方案
解决方案:单查询实现需求
可以通过单查询实现,以下提供原生SQL和Spring Data JPA两种写法:
原生SQL写法(PostgreSQL)
SELECT a.* FROM table_a a JOIN table_b b1 ON a.id = b1.id AND b1.country = 'country1' LEFT JOIN table_b b2 ON a.id = b2.id AND b2.country = 'country2' WHERE b2.id IS NULL;
逻辑说明:
- 先通过
JOIN筛选出关联Table B中存在country1的Table A记录 - 再用
LEFT JOIN关联Table B的country2条目,通过WHERE b2.id IS NULL确保这些记录不存在country2的关联
Spring Data JPA写法(JPQL)
关联属性写法
在Repository接口中添加如下方法(假设TableA实体中存在名为tableBs的集合属性关联TableB):
@Query("SELECT a FROM TableA a " + "JOIN a.tableBs b1 ON b1.country = :country1 " + "LEFT JOIN a.tableBs b2 ON b2.country = :country2 " + "WHERE b2 IS NULL") List<TableA> findByHasCountry1ButNotCountry2(@Param("country1") String country1, @Param("country2") String country2);
子查询写法
如果实体关联定义不明确,可使用更直观的子查询方式:
@Query("SELECT a FROM TableA a " + "WHERE EXISTS (SELECT b FROM TableB b WHERE b.id = a.id AND b.country = :country1) " + "AND NOT EXISTS (SELECT b FROM TableB b WHERE b.id = a.id AND b.country = :country2)") List<TableA> findByHasCountry1ButNotCountry2(@Param("country1") String country1, @Param("country2") String country2);
内容的提问来源于stack exchange,提问作者Joe
相关产品推荐
相关产品推荐

