我们正在使用spring-data-jpa-1.2.0.RELEASE.jar中的org.springframework.data.jpa.repository.JpaSpecificationExecutor.findAll(Specification arg0,Pageable arg1)。 已在PageRequest中设置了提取大小1000。 我们在数据库视图中有超过60000条记录。 单个客户可以拥有n条记录。 这意味着它将在60次提取中获得整个数据。 如果在一次阅读中挑选了客户数据,那么我们就是好的。
行客户
*********************** CASE 1
998客户A
999客户A
1000客户A
*********************** Page End
1001客户B
1002客户B
否则,如果客户数据分布在两次读取中,那么我们就会遇到严重的问题
行客户 ***********************案例2
998客户X
999客户X
1000客户X
**********************页面结束 -
1001客户X
1002客户X
在这种情况下,客户X的记录与数据库不一致。我们可以看到X客户的重复记录,这意味着客户X的一些原始行缺失。 我们从page.getContent()获得现有行的副本。但客户X的总体数量始终保持不变。
当案例1中没有重叠时,问题不会发生,并且使用sql developer从数据库直接读取总是给出正确的行。 代码中还提供了额外的排序,但删除了排序并进行了检查,结果仍然相同。 但是,如果读取的行数增加到非常大的值,即30000,这意味着只有2个读取,则只有客户的重复数据在第30和31页之间重叠。 如果数据库中的数据较少(300行),那么即使客户在2次读取中也没有问题,也没有问题。 对我来说有点困惑请给我一些提示。
答案 0 :(得分:1)
在规范中的query.distinct(true)
方法中使用toPredicate
。然后它只会获取不同的结果。
示例:
public class CustomSpecification implements Specification<MyObject> {
private MyCriteria criteria;
public CustomSpecification(MyCriteria criteria) {
this.criteria = criteria;
}
@Override
public Predicate toPredicate(Root<MyObject> root, CriteriaQuery<?> query, CriteriaBuilder builder) {
Predicate myPredicate =...;
query.distinct(true);
return myPredicate;
}
}