【问题标题】:JPA Criteria API Predicates for multiple requirements in child collection子集合中多个需求的 JPA Criteria API 谓词
【发布时间】:2016-06-23 21:41:15
【问题描述】:

考虑以下场景:

public class Parent {
    private List<Child> childs;
}

public class Child {
    private Target target;
    private Value value;
}

public class Target {
    private Long id;
}

public class Value {
    private Long id;
}

对于每个确定的目标对象,父对象将具有具有值对象的子对象。

我得到HashMap&lt;Long&gt;, List&lt;Long&gt;&gt; 格式的过滤器,其中键是目标对象的 ID,值是所需值对象 ID 的列表。 例如,我需要使用 JPA Criteria API 获得以下条件的所有父母:

  • 有 targetId 为 1 且 valueId 在 (1,2,3) 中的孩子
  • AND 有 targetId 为 2 且 valueId 在 (1,4) 中的子项

所以我需要排除不满足所有要求的结果。有没有办法使用 JPA Criteria API 来实现这一点。我尝试了以下方法:

List<Predicate> predicates = new ArrayList<>();
...
List<Predicate> subPredicates = new ArrayList<>();
Path<Child> child = root.join(Parent_.child, JoinType.LEFT);
for (Map.Entry<Long, List<Long>> entry : map.entrySet()) {
    Long targetId = entry.getKey();
    List<Long> valueIds = entry.getValue();
    subPredicates.add(cb.and(cb.equal(child.get(Child_.target), targetId), child.get(Child_.value).in(valueIds)));
}
predicates.add(cb.and(subPredicates.toArray(new Predicate[subPredicates.size()])));

但显然它不起作用。这种类结构甚至可能吗?谁能帮我解决这个问题?

【问题讨论】:

  • 你的方法看起来不错。它出什么问题了?包括错误和/或查询输出。如果它不起作用,我会尝试使用如下所述的子查询列表:stackoverflow.com/a/4668015/870122
  • 你的问题很困惑。您是通过了 Map> 还是通过了 Map>, ?>。如果是后者,价值是多少?

标签: java jpa spring-data-jpa criteria-api jpa-2.1


【解决方案1】:

我会尝试创建两个连接,都与子表一起,并在每个连接中设置一个条件,因此如果两者之一不满足,则不会出现任何结果。

例如:

Path<Child> childCondition1 = root.join(Parent_.child, JoinType.INNER);
Path<Child> childCondition2 = root.join(Parent_.child, JoinType.INNER);

List<Predicate> predicates = new ArrayList<>();
predicates.add(cb.and([condition1 over childCondition1],[condition2 over childCondition2,]));

另一种选择(提前使用 JPA 2.1,可能更有效):

Path<Child> childCondition1 = root.join(Parent_.child, JoinType.INNER);
    childCondition1.on([condition1 over childCondition1]);
Path<Child> childCondition2 = root.join(Parent_.child, JoinType.INNER);
    childCondition2.on([condition2 over childCondition2]);

【讨论】:

    猜你喜欢
    • 2020-10-17
    • 1970-01-01
    • 1970-01-01
    • 2019-06-22
    • 2017-02-22
    • 1970-01-01
    • 2015-01-14
    • 2014-08-10
    • 1970-01-01
    相关资源
    最近更新 更多