diff --git a/core/src/main/java/org/elasticsearch/index/query/HasChildQueryBuilder.java b/core/src/main/java/org/elasticsearch/index/query/HasChildQueryBuilder.java index c045ea2f649..1301f15cc7d 100644 --- a/core/src/main/java/org/elasticsearch/index/query/HasChildQueryBuilder.java +++ b/core/src/main/java/org/elasticsearch/index/query/HasChildQueryBuilder.java @@ -352,7 +352,17 @@ public class HasChildQueryBuilder extends AbstractQueryBuilder terms) throws IOException { - // skip all geo queries, see https://issues.apache.org/jira/browse/LUCENE-7293 and - // https://github.com/elastic/elasticsearch/issues/17537 - if (query instanceof GeoPointInBBoxQuery == false) { - super.extract(query, boost, terms); + if (query instanceof GeoPointInBBoxQuery) { + // skip all geo queries, see https://issues.apache.org/jira/browse/LUCENE-7293 and + // https://github.com/elastic/elasticsearch/issues/17537 + return; + } else if (query instanceof HasChildQueryBuilder.LateParsingQuery) { + // skip has_child or has_parent queries, see: https://github.com/elastic/elasticsearch/issues/14999 + return; } + + super.extract(query, boost, terms); } } } diff --git a/core/src/test/java/org/elasticsearch/search/child/ChildQuerySearchIT.java b/core/src/test/java/org/elasticsearch/search/child/ChildQuerySearchIT.java index 68679e89ae6..67f9c8f2cf3 100644 --- a/core/src/test/java/org/elasticsearch/search/child/ChildQuerySearchIT.java +++ b/core/src/test/java/org/elasticsearch/search/child/ChildQuerySearchIT.java @@ -32,8 +32,12 @@ import org.elasticsearch.common.lucene.search.function.FiltersFunctionScoreQuery import org.elasticsearch.common.settings.Settings; import org.elasticsearch.common.unit.TimeValue; import org.elasticsearch.index.IndexModule; +import org.elasticsearch.index.query.BoolQueryBuilder; import org.elasticsearch.index.query.HasChildQueryBuilder; +import org.elasticsearch.index.query.HasParentQueryBuilder; import org.elasticsearch.index.query.IdsQueryBuilder; +import org.elasticsearch.index.query.MatchAllQueryBuilder; +import org.elasticsearch.index.query.MatchQueryBuilder; import org.elasticsearch.index.query.QueryBuilder; import org.elasticsearch.index.query.QueryBuilders; import org.elasticsearch.index.query.functionscore.FunctionScoreQueryBuilder; @@ -43,6 +47,8 @@ import org.elasticsearch.search.aggregations.bucket.filter.Filter; import org.elasticsearch.search.aggregations.bucket.global.Global; import org.elasticsearch.search.aggregations.bucket.terms.Terms; import org.elasticsearch.search.builder.SearchSourceBuilder; +import org.elasticsearch.search.highlight.HighlightBuilder; +import org.elasticsearch.search.highlight.HighlightField; import org.elasticsearch.search.sort.SortBuilders; import org.elasticsearch.search.sort.SortOrder; import org.elasticsearch.test.ESIntegTestCase; @@ -1889,4 +1895,43 @@ public class ChildQuerySearchIT extends ESIntegTestCase { QueryBuilders.hasChildQuery("child-type", new IdsQueryBuilder().addIds("child-id"), ScoreMode.None)).get(); assertSearchHits(searchResponse, "parent-id"); } + + public void testHighlighersIgnoreParentChild() { + assertAcked(prepareCreate("test") + .addMapping("parent-type", "searchText", "type=text,term_vector=with_positions_offsets,index_options=offsets") + .addMapping("child-type", "_parent", "type=parent-type", "searchText", + "type=text,term_vector=with_positions_offsets,index_options=offsets")); + client().prepareIndex("test", "parent-type", "parent-id").setSource("searchText", "quick brown fox").get(); + client().prepareIndex("test", "child-type", "child-id").setParent("parent-id").setSource("searchText", "quick brown fox").get(); + refresh(); + + String[] highlightTypes = new String[] {"plain", "fvh", "postings"}; + for (String highlightType : highlightTypes) { + logger.info("Testing with highlight type [{}]", highlightType); + SearchResponse searchResponse = client().prepareSearch("test") + .setQuery(new BoolQueryBuilder() + .must(new MatchQueryBuilder("searchText", "fox")) + .must(new HasChildQueryBuilder("child-type", new MatchAllQueryBuilder(), ScoreMode.None)) + ) + .highlighter(new HighlightBuilder().field(new HighlightBuilder.Field("searchText").highlighterType(highlightType))) + .get(); + assertHitCount(searchResponse, 1); + assertThat(searchResponse.getHits().getAt(0).id(), equalTo("parent-id")); + HighlightField highlightField = searchResponse.getHits().getAt(0).getHighlightFields().get("searchText"); + assertThat(highlightField.getFragments()[0].string(), equalTo("quick brown fox")); + + searchResponse = client().prepareSearch("test") + .setQuery(new BoolQueryBuilder() + .must(new MatchQueryBuilder("searchText", "fox")) + .must(new HasParentQueryBuilder("parent-type", new MatchAllQueryBuilder(), false)) + ) + .highlighter(new HighlightBuilder().field(new HighlightBuilder.Field("searchText").highlighterType(highlightType))) + .get(); + assertHitCount(searchResponse, 1); + assertThat(searchResponse.getHits().getAt(0).id(), equalTo("child-id")); + highlightField = searchResponse.getHits().getAt(0).getHighlightFields().get("searchText"); + assertThat(highlightField.getFragments()[0].string(), equalTo("quick brown fox")); + } + } + }