Don't override originalQuery with request filters

These filters leak into highlighting and probably other places and cause
things like the type name to be highlighted when using
requireFieldMatch=false. We could have special hacks to keep them out of
highlighting but it feals better to keep them out of any variable named
"originalQuery".

Closes #15689
This commit is contained in:
Nik Everett 2016-01-06 12:12:20 -05:00
parent 664d67d41d
commit d3a4a9f871
4 changed files with 46 additions and 21 deletions

View File

@ -182,11 +182,10 @@ public class TransportValidateQueryAction extends TransportBroadcastAction<Valid
searchContext.preProcess();
valid = true;
if (request.explain()) {
explanation = searchContext.parsedQuery().query().toString();
}
if (request.rewrite()) {
explanation = getRewrittenQuery(searcher.searcher(), searchContext.query());
} else if (request.explain()) {
explanation = searchContext.filteredQuery().query().toString();
}
} catch (QueryShardException|ParsingException e) {
valid = false;

View File

@ -125,7 +125,20 @@ public class DefaultSearchContext extends SearchContext {
private Sort sort;
private Float minimumScore;
private boolean trackScores = false; // when sorting, track scores as well...
/**
* The original query as sent by the user without the types and aliases
* applied. Putting things in here leaks them into highlighting so don't add
* things like the type filter or alias filters.
*/
private ParsedQuery originalQuery;
/**
* Just like originalQuery but with the filters from types and aliases
* applied.
*/
private ParsedQuery filteredQuery;
/**
* The query to actually execute.
*/
private Query query;
private ParsedQuery postFilter;
private Query aliasFilter;
@ -209,22 +222,7 @@ public class DefaultSearchContext extends SearchContext {
if (queryBoost() != AbstractQueryBuilder.DEFAULT_BOOST) {
parsedQuery(new ParsedQuery(new FunctionScoreQuery(query(), new WeightFactorFunction(queryBoost)), parsedQuery()));
}
Query searchFilter = searchFilter(types());
if (searchFilter != null) {
if (Queries.isConstantMatchAllQuery(query())) {
Query q = new ConstantScoreQuery(searchFilter);
if (query().getBoost() != AbstractQueryBuilder.DEFAULT_BOOST) {
q = new BoostQuery(q, query().getBoost());
}
parsedQuery(new ParsedQuery(q, parsedQuery()));
} else {
BooleanQuery filtered = new BooleanQuery.Builder()
.add(query(), Occur.MUST)
.add(searchFilter, Occur.FILTER)
.build();
parsedQuery(new ParsedQuery(filtered, parsedQuery()));
}
}
filteredQuery(buildFilteredQuery());
try {
this.query = searcher().rewrite(this.query);
} catch (IOException e) {
@ -232,6 +230,26 @@ public class DefaultSearchContext extends SearchContext {
}
}
private ParsedQuery buildFilteredQuery() {
Query searchFilter = searchFilter(types());
if (searchFilter == null) {
return originalQuery;
}
Query result;
if (Queries.isConstantMatchAllQuery(query())) {
result = new ConstantScoreQuery(searchFilter);
if (query().getBoost() != AbstractQueryBuilder.DEFAULT_BOOST) {
result = new BoostQuery(result, query().getBoost());
}
} else {
result = new BooleanQuery.Builder()
.add(query, Occur.MUST)
.add(searchFilter, Occur.FILTER)
.build();
}
return new ParsedQuery(result, originalQuery);
}
@Override
public Query searchFilter(String[] types) {
Query filter = mapperService().searchFilter(types);
@ -546,6 +564,15 @@ public class DefaultSearchContext extends SearchContext {
return this;
}
public ParsedQuery filteredQuery() {
return filteredQuery;
}
private void filteredQuery(ParsedQuery filteredQuery) {
this.filteredQuery = filteredQuery;
this.query = filteredQuery.query();
}
@Override
public ParsedQuery parsedQuery() {
return this.originalQuery;

View File

@ -2571,7 +2571,6 @@ public class HighlighterSearchIT extends ESIntegTestCase {
}
}
@AwaitsFix(bugUrl="Broken now that BoostingQuery does not extend BooleanQuery anymore")
public void testFastVectorHighlighterPhraseBoost() throws Exception {
assertAcked(prepareCreate("test").addMapping("type1", type1TermVectorMapping()));

View File

@ -105,7 +105,7 @@ public class SimpleValidateQueryIT extends ESIntegTestCase {
}
for (Client client : internalCluster()) {
ValidateQueryResponse response = client.admin().indices().prepareValidateQuery("test")
ValidateQueryResponse response = client.admin().indices().prepareValidateQuery("test")
.setQuery(QueryBuilders.queryStringQuery("foo"))
.setExplain(true)
.execute().actionGet();