Spring-Data-Elasticsearch链接" OR"标准与" AND"标准

时间:2018-02-02 17:25:34

标签: spring-data spring-data-elasticsearch

将AND标准链接到AND标准不能按预期工作。说我想找到所有绿色的彩色衣物,这些物品都是免税的或来自印度。我希望以下代码能够实现这一目标:

List<Criteria> andConditions = new ArrayList<>();
List<Criteria> orConditions = new ArrayList<>();

    andConditions.add(new Criteria("color").is("green"));
    andConditions.add(new Criteria("fabric").is("cotton"));

    orConditions.add(new Criteria("countryOfOrigin").is("INDIA"));
    orConditions.add(new Criteria("isDutyFree").is(true));


    Criteria andCriteria=new Criteria();
    Criteria orCriteria=null; //to avoid new Criteria().or(firstCriteriaInLoopBelow), since new Criteria() might match  everything...

    for(Criteria condition:andConditions){
       andCriteria=andCriteria.and(condition);
    }
    for(Criteria condition:orConditions){
       if(orCriteria==null){
           orCriteria=condition;
       }else{
           orCriteria=orCriteria.or(condition);
       }
    }


andCriteria=andCritiera.and(orCriteria);
CriteriaQuery query = new CriteriaQuery(andCriteria).setPageable(page);
elasticsearchTemplate.queryForPage(query, ClothingArticle.class)

相反,查询似乎完全忽略了andCriteria,并且只是尊重OR标准。换句话说,我收回所有在印度制造的衣物或免税品,不受颜色或面料的影响。

我在Spring的信息中心找到了这张Jira票:DATAES-30 标题为&#39; &#34;或&#34; CriteriaQuery中的条件未正确生成&#39;

但是这张票看起来很旧,而且破坏了“或者”。功能似乎是一种严重缺乏功能。

是否有人建议将OR链接到和AND?

谢谢!

1 个答案:

答案 0 :(得分:0)

我能够使用SearchQuery实现所需的行为。看起来默认的minimumShouldMatch是0,就像之前我将minimumShouldMatch设置为1一样,SearchQuery具有我在使用Criteria时遇到的相同行为。

BoolQueryBuilder filter= QueryBuilders.boolQuery()
          .must(QueryBuilders.termQuery("color", "green"))
          .must(QueryBuilders.termQuery("fabric","cotton"))
          .should(QueryBuilders.termQuery("countryOfOrigin","India"))
          .should(QueryBuilders.termQuery("isDutyFree",true))
          .minimumShouldMatch(1);

SearchQuery query = new NativeSearchQueryBuilder()
                .withQuery(matchAllQuery())
                .withFilter(filter)
                .withPageable(pageable)
                .build();

Page<ClothingArticle> clothes = elasticsearchTemplate.queryForPage(searchQuery, ClothingArticle.class);