Pure disjunctions should rewrite to a MatchNoneQueryBuilder (#48557) (#49673)

Closes #48475
This commit is contained in:
Adrien Grand 2019-11-28 15:54:32 +01:00 committed by GitHub
parent e528b41cf2
commit 1824a2fa58
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 22 additions and 0 deletions

View File

@ -424,12 +424,19 @@ public class BoolQueryBuilder extends AbstractQueryBuilder<BoolQueryBuilder> {
changed |= rewriteClauses(queryRewriteContext, mustNotClauses, newBuilder::mustNot);
changed |= rewriteClauses(queryRewriteContext, filterClauses, newBuilder::filter);
changed |= rewriteClauses(queryRewriteContext, shouldClauses, newBuilder::should);
// early termination when must clause is empty and optional clauses is returning MatchNoneQueryBuilder
if(mustClauses.size() == 0 && filterClauses.size() == 0 && shouldClauses.size() > 0
&& newBuilder.shouldClauses.stream().allMatch(b -> b instanceof MatchNoneQueryBuilder)) {
return new MatchNoneQueryBuilder();
}
// lets do some early termination and prevent any kind of rewriting if we have a mandatory query that is a MatchNoneQueryBuilder
Optional<QueryBuilder> any = Stream.concat(newBuilder.mustClauses.stream(), newBuilder.filterClauses.stream())
.filter(b -> b instanceof MatchNoneQueryBuilder).findAny();
if (any.isPresent()) {
return any.get();
}
if (changed) {
newBuilder.adjustPureNegative = adjustPureNegative;
newBuilder.minimumShouldMatch = minimumShouldMatch;

View File

@ -371,5 +371,20 @@ public class BoolQueryBuilderTests extends AbstractQueryTestCase<BoolQueryBuilde
.filter(new MatchNoneQueryBuilder()));
rewritten = Rewriteable.rewrite(boolQueryBuilder, createShardContext());
assertEquals(new MatchNoneQueryBuilder(), rewritten);
boolQueryBuilder = new BoolQueryBuilder();
boolQueryBuilder.should(new WrapperQueryBuilder(new MatchNoneQueryBuilder().toString()));
rewritten = Rewriteable.rewrite(boolQueryBuilder, createShardContext());
assertEquals(new MatchNoneQueryBuilder(), rewritten);
boolQueryBuilder = new BoolQueryBuilder();
boolQueryBuilder.should(new TermQueryBuilder("foo", "bar"));
boolQueryBuilder.should(new WrapperQueryBuilder(new MatchNoneQueryBuilder().toString()));
rewritten = Rewriteable.rewrite(boolQueryBuilder, createShardContext());
assertNotEquals(new MatchNoneQueryBuilder(), rewritten);
boolQueryBuilder = new BoolQueryBuilder();
rewritten = Rewriteable.rewrite(boolQueryBuilder, createShardContext());
assertNotEquals(new MatchNoneQueryBuilder(), rewritten);
}
}