-
Notifications
You must be signed in to change notification settings - Fork 25.2k
Check for runtime field loops in queries #61927
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from 1 commit
c39360a
0716b27
9ce7174
72c1b8b
f780a42
4bc988b
b66a16d
45d124b
bef47e2
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -9,6 +9,7 @@ | |
import org.apache.lucene.analysis.TokenStream; | ||
import org.apache.lucene.search.MultiTermQuery; | ||
import org.apache.lucene.search.Query; | ||
import org.apache.lucene.search.MultiTermQuery.RewriteMethod; | ||
import org.apache.lucene.search.spans.SpanMultiTermQueryWrapper; | ||
import org.apache.lucene.search.spans.SpanQuery; | ||
import org.elasticsearch.ElasticsearchException; | ||
|
@@ -19,24 +20,33 @@ | |
import org.elasticsearch.index.mapper.TextSearchInfo; | ||
import org.elasticsearch.index.query.QueryShardContext; | ||
import org.elasticsearch.script.Script; | ||
import org.elasticsearch.search.lookup.SearchLookup; | ||
|
||
import java.io.IOException; | ||
import java.time.ZoneId; | ||
import java.util.List; | ||
import java.util.Locale; | ||
import java.util.Map; | ||
import java.util.function.BiFunction; | ||
|
||
import static org.elasticsearch.search.SearchService.ALLOW_EXPENSIVE_QUERIES; | ||
|
||
/** | ||
* Abstract base {@linkplain MappedFieldType} for scripted fields. | ||
*/ | ||
abstract class AbstractScriptMappedFieldType extends MappedFieldType { | ||
abstract class AbstractScriptMappedFieldType<LeafFactory> extends MappedFieldType { | ||
protected final Script script; | ||
private final BiFunction<Map<String, Object>, SearchLookup, LeafFactory> factory; | ||
|
||
AbstractScriptMappedFieldType(String name, Script script, Map<String, String> meta) { | ||
AbstractScriptMappedFieldType( | ||
String name, | ||
Script script, | ||
BiFunction<Map<String, Object>, SearchLookup, LeafFactory> factory, | ||
Map<String, String> meta | ||
) { | ||
super(name, false, false, TextSearchInfo.SIMPLE_MATCH_ONLY, meta); | ||
this.script = script; | ||
this.factory = factory; | ||
} | ||
|
||
protected abstract String runtimeType(); | ||
|
@@ -61,6 +71,26 @@ public final boolean isAggregatable() { | |
return true; | ||
} | ||
|
||
/** | ||
* Create a script leaf factory. | ||
*/ | ||
protected final LeafFactory leafFactory(SearchLookup searchLookup) { | ||
return factory.apply(script.getParams(), searchLookup); | ||
} | ||
|
||
/** | ||
* Create a script leaf factory for queries. | ||
*/ | ||
protected final LeafFactory leafFactory(QueryShardContext context) { | ||
/* | ||
* Forking here causes us to count this field in the field data loop | ||
* detection code as though we were resolving field data for this field. | ||
* We're not, but running the query is close enough. | ||
*/ | ||
return leafFactory(context.lookup().forkAndTrackFieldReferences(name())); | ||
} | ||
|
||
@Override | ||
public abstract Query termsQuery(List<?> values, QueryShardContext context); | ||
|
||
@Override | ||
|
@@ -91,6 +121,7 @@ protected abstract Query rangeQuery( | |
QueryShardContext context | ||
); | ||
|
||
@Override | ||
public Query fuzzyQuery( | ||
Object value, | ||
Fuzziness fuzziness, | ||
|
@@ -102,38 +133,47 @@ public Query fuzzyQuery( | |
throw new IllegalArgumentException(unsupported("fuzzy", "keyword and text")); | ||
} | ||
|
||
@Override | ||
public Query prefixQuery(String value, MultiTermQuery.RewriteMethod method, QueryShardContext context) { | ||
throw new IllegalArgumentException(unsupported("prefix", "keyword, text and wildcard")); | ||
} | ||
|
||
@Override | ||
public Query wildcardQuery(String value, MultiTermQuery.RewriteMethod method, QueryShardContext context) { | ||
throw new IllegalArgumentException(unsupported("wildcard", "keyword, text and wildcard")); | ||
} | ||
|
||
@Override | ||
public Query regexpQuery( | ||
String value, | ||
int flags, | ||
int syntaxFlags, | ||
int matchFlags, | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Missing this was a bug that causes regexes not to work at all! |
||
int maxDeterminizedStates, | ||
MultiTermQuery.RewriteMethod method, | ||
RewriteMethod method, | ||
QueryShardContext context | ||
) { | ||
throw new IllegalArgumentException(unsupported("regexp", "keyword and text")); | ||
} | ||
|
||
@Override | ||
public abstract Query existsQuery(QueryShardContext context); | ||
|
||
@Override | ||
public Query phraseQuery(TokenStream stream, int slop, boolean enablePositionIncrements) throws IOException { | ||
throw new IllegalArgumentException(unsupported("phrase", "text")); | ||
} | ||
|
||
@Override | ||
public Query multiPhraseQuery(TokenStream stream, int slop, boolean enablePositionIncrements) throws IOException { | ||
throw new IllegalArgumentException(unsupported("phrase", "text")); | ||
} | ||
|
||
@Override | ||
public Query phrasePrefixQuery(TokenStream stream, int slop, int maxExpansions) throws IOException { | ||
throw new IllegalArgumentException(unsupported("phrase prefix", "text")); | ||
} | ||
|
||
@Override | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I've seen this popup in this and some other PR, can we merge this fix separately? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I've pushed a fix for this to master and 7.x. I'll merge that into this branch now. |
||
public SpanQuery spanPrefixQuery(String value, SpanMultiTermQueryWrapper.SpanRewriteMethod method, QueryShardContext context) { | ||
throw new IllegalArgumentException(unsupported("span prefix", "text")); | ||
} | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I pulled this function into the superclass because it the "for query" version of it is tricky. We could probably avoid the type parameter if we really wanted to by being a bit more tricky, but I'm not sure it is worth it.