diff --git a/modules/elasticsearch/src/main/java/org/apache/lucene/queryParser/MapperQueryParser.java b/modules/elasticsearch/src/main/java/org/apache/lucene/queryParser/MapperQueryParser.java
index 758fda70c14..e9c68854be7 100644
--- a/modules/elasticsearch/src/main/java/org/apache/lucene/queryParser/MapperQueryParser.java
+++ b/modules/elasticsearch/src/main/java/org/apache/lucene/queryParser/MapperQueryParser.java
@@ -24,7 +24,6 @@ import org.apache.lucene.analysis.tokenattributes.CharTermAttribute;
import org.apache.lucene.index.Term;
import org.apache.lucene.search.BooleanClause;
import org.apache.lucene.search.FuzzyQuery;
-import org.apache.lucene.search.MultiTermQuery;
import org.apache.lucene.search.Query;
import org.elasticsearch.common.collect.ImmutableMap;
import org.elasticsearch.common.io.FastStringReader;
@@ -84,7 +83,7 @@ public class MapperQueryParser extends QueryParser {
public void reset(QueryParserSettings settings) {
this.field = settings.defaultField();
this.analyzer = settings.analyzer();
- setMultiTermRewriteMethod(MultiTermQuery.CONSTANT_SCORE_AUTO_REWRITE_DEFAULT);
+ setMultiTermRewriteMethod(settings.rewriteMethod());
setEnablePositionIncrements(settings.enablePositionIncrements());
setAutoGeneratePhraseQueries(settings.autoGeneratePhraseQueries());
setAllowLeadingWildcard(settings.allowLeadingWildcard());
diff --git a/modules/elasticsearch/src/main/java/org/apache/lucene/queryParser/QueryParserSettings.java b/modules/elasticsearch/src/main/java/org/apache/lucene/queryParser/QueryParserSettings.java
index 9790ea6d821..cc2a83e874d 100644
--- a/modules/elasticsearch/src/main/java/org/apache/lucene/queryParser/QueryParserSettings.java
+++ b/modules/elasticsearch/src/main/java/org/apache/lucene/queryParser/QueryParserSettings.java
@@ -21,6 +21,7 @@ package org.apache.lucene.queryParser;
import org.apache.lucene.analysis.Analyzer;
import org.apache.lucene.search.FuzzyQuery;
+import org.apache.lucene.search.MultiTermQuery;
/**
* @author kimchy (shay.banon)
@@ -41,6 +42,7 @@ public class QueryParserSettings {
private boolean analyzeWildcard = false;
private boolean escape = false;
private Analyzer analyzer = null;
+ private MultiTermQuery.RewriteMethod rewriteMethod = MultiTermQuery.CONSTANT_SCORE_AUTO_REWRITE_DEFAULT;
public String queryString() {
return queryString;
@@ -154,6 +156,14 @@ public class QueryParserSettings {
this.analyzeWildcard = analyzeWildcard;
}
+ public MultiTermQuery.RewriteMethod rewriteMethod() {
+ return this.rewriteMethod;
+ }
+
+ public void rewriteMethod(MultiTermQuery.RewriteMethod rewriteMethod) {
+ this.rewriteMethod = rewriteMethod;
+ }
+
@Override public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
diff --git a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/FieldQueryBuilder.java b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/FieldQueryBuilder.java
index 4cd08c20598..a4b798a26fc 100644
--- a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/FieldQueryBuilder.java
+++ b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/FieldQueryBuilder.java
@@ -65,6 +65,8 @@ public class FieldQueryBuilder extends BaseQueryBuilder {
private boolean extraSet = false;
+ private String rewrite;
+
/**
* A query that executes the query string against a field. It is a simplified
* version of {@link QueryStringQueryBuilder} that simply runs against
@@ -268,6 +270,12 @@ public class FieldQueryBuilder extends BaseQueryBuilder {
return this;
}
+ public FieldQueryBuilder rewrite(String rewrite) {
+ this.rewrite = rewrite;
+ extraSet = true;
+ return this;
+ }
+
@Override public void doXContent(XContentBuilder builder, Params params) throws IOException {
builder.startObject(FieldQueryParser.NAME);
if (!extraSet) {
@@ -308,6 +316,9 @@ public class FieldQueryBuilder extends BaseQueryBuilder {
if (analyzeWildcard != null) {
builder.field("analyze_wildcard", analyzeWildcard);
}
+ if (rewrite != null) {
+ builder.field("rewrite", rewrite);
+ }
builder.endObject();
}
builder.endObject();
diff --git a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/FieldQueryParser.java b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/FieldQueryParser.java
index a4505372d47..4a9fc7d1dd0 100644
--- a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/FieldQueryParser.java
+++ b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/FieldQueryParser.java
@@ -25,6 +25,7 @@ import org.apache.lucene.queryParser.QueryParserSettings;
import org.apache.lucene.search.Query;
import org.elasticsearch.common.inject.Inject;
import org.elasticsearch.common.xcontent.XContentParser;
+import org.elasticsearch.index.query.support.QueryParsers;
import java.io.IOException;
@@ -93,6 +94,8 @@ public class FieldQueryParser implements QueryParser {
qpSettings.escape(parser.booleanValue());
} else if ("analyze_wildcard".equals(currentFieldName) || "analyzeWildcard".equals(currentFieldName)) {
qpSettings.analyzeWildcard(parser.booleanValue());
+ } else if ("rewrite".equals(currentFieldName)) {
+ qpSettings.rewriteMethod(QueryParsers.parseRewriteMethod(parser.textOrNull()));
}
}
}
diff --git a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/PrefixQueryBuilder.java b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/PrefixQueryBuilder.java
index 2f28041c895..02d90def3ad 100644
--- a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/PrefixQueryBuilder.java
+++ b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/PrefixQueryBuilder.java
@@ -36,6 +36,8 @@ public class PrefixQueryBuilder extends BaseQueryBuilder {
private float boost = -1;
+ private String rewrite;
+
/**
* A Query that matches documents containing terms with a specified prefix.
*
@@ -56,14 +58,24 @@ public class PrefixQueryBuilder extends BaseQueryBuilder {
return this;
}
+ public PrefixQueryBuilder rewrite(String rewrite) {
+ this.rewrite = rewrite;
+ return this;
+ }
+
@Override public void doXContent(XContentBuilder builder, Params params) throws IOException {
builder.startObject(PrefixQueryParser.NAME);
- if (boost == -1) {
+ if (boost == -1 && rewrite == null) {
builder.field(name, prefix);
} else {
builder.startObject(name);
builder.field("prefix", prefix);
- builder.field("boost", boost);
+ if (boost != -1) {
+ builder.field("boost", boost);
+ }
+ if (rewrite != null) {
+ builder.field("rewrite", rewrite);
+ }
builder.endObject();
}
builder.endObject();
diff --git a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/PrefixQueryParser.java b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/PrefixQueryParser.java
index ecd7956562f..19fd9435c9a 100644
--- a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/PrefixQueryParser.java
+++ b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/PrefixQueryParser.java
@@ -20,12 +20,12 @@
package org.elasticsearch.index.query;
import org.apache.lucene.index.Term;
-import org.apache.lucene.search.MultiTermQuery;
import org.apache.lucene.search.PrefixQuery;
import org.apache.lucene.search.Query;
import org.elasticsearch.common.inject.Inject;
import org.elasticsearch.common.xcontent.XContentParser;
import org.elasticsearch.index.mapper.MapperService;
+import org.elasticsearch.index.query.support.QueryParsers;
import java.io.IOException;
@@ -51,7 +51,7 @@ public class PrefixQueryParser implements QueryParser {
XContentParser.Token token = parser.nextToken();
assert token == XContentParser.Token.FIELD_NAME;
String fieldName = parser.currentName();
-
+ String rewriteMethod = null;
String value = null;
float boost = 1.0f;
@@ -68,6 +68,8 @@ public class PrefixQueryParser implements QueryParser {
value = parser.text();
} else if ("boost".equals(currentFieldName)) {
boost = parser.floatValue();
+ } else if ("rewrite".equals(currentFieldName)) {
+ rewriteMethod = parser.textOrNull();
}
}
}
@@ -90,7 +92,7 @@ public class PrefixQueryParser implements QueryParser {
}
PrefixQuery query = new PrefixQuery(new Term(fieldName, value));
- query.setRewriteMethod(MultiTermQuery.CONSTANT_SCORE_AUTO_REWRITE_DEFAULT);
+ query.setRewriteMethod(QueryParsers.parseRewriteMethod(rewriteMethod));
query.setBoost(boost);
return wrapSmartNameQuery(query, smartNameFieldMappers, parseContext);
}
diff --git a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/QueryStringQueryBuilder.java b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/QueryStringQueryBuilder.java
index 2a9350e846b..3c37b50a4f9 100644
--- a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/QueryStringQueryBuilder.java
+++ b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/QueryStringQueryBuilder.java
@@ -78,6 +78,8 @@ public class QueryStringQueryBuilder extends BaseQueryBuilder {
private float tieBreaker = -1;
+ private String rewrite = null;
+
public QueryStringQueryBuilder(String queryString) {
this.queryString = queryString;
}
@@ -234,6 +236,11 @@ public class QueryStringQueryBuilder extends BaseQueryBuilder {
return this;
}
+ public QueryStringQueryBuilder rewrite(String rewrite) {
+ this.rewrite = rewrite;
+ return this;
+ }
+
/**
* Sets the boost for this query. Documents matching this query will (in addition to the normal
* weightings) have their score multiplied by the boost provided.
@@ -302,6 +309,9 @@ public class QueryStringQueryBuilder extends BaseQueryBuilder {
if (analyzeWildcard != null) {
builder.field("analyze_wildcard", analyzeWildcard);
}
+ if (rewrite != null) {
+ builder.field("rewrite", rewrite);
+ }
builder.endObject();
}
}
diff --git a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/QueryStringQueryParser.java b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/QueryStringQueryParser.java
index 376f782088b..18a13b52a5f 100644
--- a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/QueryStringQueryParser.java
+++ b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/QueryStringQueryParser.java
@@ -31,6 +31,7 @@ import org.elasticsearch.common.trove.impl.Constants;
import org.elasticsearch.common.trove.map.hash.TObjectFloatHashMap;
import org.elasticsearch.common.xcontent.XContentParser;
import org.elasticsearch.index.mapper.internal.AllFieldMapper;
+import org.elasticsearch.index.query.support.QueryParsers;
import java.io.IOException;
@@ -144,6 +145,8 @@ public class QueryStringQueryParser implements QueryParser {
qpSettings.tieBreaker(parser.floatValue());
} else if ("analyze_wildcard".equals(currentFieldName) || "analyzeWildcard".equals(currentFieldName)) {
qpSettings.analyzeWildcard(parser.booleanValue());
+ } else if ("rewrite".equals(currentFieldName)) {
+ qpSettings.rewriteMethod(QueryParsers.parseRewriteMethod(parser.textOrNull()));
}
}
}
diff --git a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/WildcardQueryBuilder.java b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/WildcardQueryBuilder.java
index 720e6896d7b..79589f53c0f 100644
--- a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/WildcardQueryBuilder.java
+++ b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/WildcardQueryBuilder.java
@@ -41,6 +41,8 @@ public class WildcardQueryBuilder extends BaseQueryBuilder {
private float boost = -1;
+ private String rewrite;
+
/**
* Implements the wildcard search query. Supported wildcards are *, which
* matches any character sequence (including the empty one), and ?,
@@ -57,6 +59,11 @@ public class WildcardQueryBuilder extends BaseQueryBuilder {
this.wildcard = wildcard;
}
+ public WildcardQueryBuilder rewrite(String rewrite) {
+ this.rewrite = rewrite;
+ return this;
+ }
+
/**
* Sets the boost for this query. Documents matching this query will (in addition to the normal
* weightings) have their score multiplied by the boost provided.
@@ -68,12 +75,17 @@ public class WildcardQueryBuilder extends BaseQueryBuilder {
@Override public void doXContent(XContentBuilder builder, Params params) throws IOException {
builder.startObject(WildcardQueryParser.NAME);
- if (boost == -1) {
+ if (boost == -1 && rewrite != null) {
builder.field(name, wildcard);
} else {
builder.startObject(name);
builder.field("wildcard", wildcard);
- builder.field("boost", boost);
+ if (boost != -1) {
+ builder.field("boost", boost);
+ }
+ if (rewrite != null) {
+ builder.field("rewrite", rewrite);
+ }
builder.endObject();
}
builder.endObject();
diff --git a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/WildcardQueryParser.java b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/WildcardQueryParser.java
index 4c7b40855c2..8258c2527d9 100644
--- a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/WildcardQueryParser.java
+++ b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/WildcardQueryParser.java
@@ -20,12 +20,12 @@
package org.elasticsearch.index.query;
import org.apache.lucene.index.Term;
-import org.apache.lucene.search.MultiTermQuery;
import org.apache.lucene.search.Query;
import org.apache.lucene.search.WildcardQuery;
import org.elasticsearch.common.inject.Inject;
import org.elasticsearch.common.xcontent.XContentParser;
import org.elasticsearch.index.mapper.MapperService;
+import org.elasticsearch.index.query.support.QueryParsers;
import java.io.IOException;
@@ -51,7 +51,7 @@ public class WildcardQueryParser implements QueryParser {
XContentParser.Token token = parser.nextToken();
assert token == XContentParser.Token.FIELD_NAME;
String fieldName = parser.currentName();
-
+ String rewriteMethod = null;
String value = null;
float boost = 1.0f;
@@ -68,6 +68,8 @@ public class WildcardQueryParser implements QueryParser {
value = parser.text();
} else if ("boost".equals(currentFieldName)) {
boost = parser.floatValue();
+ } else if ("rewrite".equals(currentFieldName)) {
+ rewriteMethod = parser.textOrNull();
}
}
}
@@ -90,7 +92,7 @@ public class WildcardQueryParser implements QueryParser {
}
WildcardQuery query = new WildcardQuery(new Term(fieldName, value));
- query.setRewriteMethod(MultiTermQuery.CONSTANT_SCORE_AUTO_REWRITE_DEFAULT);
+ query.setRewriteMethod(QueryParsers.parseRewriteMethod(rewriteMethod));
query.setBoost(boost);
return wrapSmartNameQuery(query, smartNameFieldMappers, parseContext);
}
diff --git a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/support/QueryParsers.java b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/support/QueryParsers.java
index 7e5e2628edf..bb61ec3b43f 100644
--- a/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/support/QueryParsers.java
+++ b/modules/elasticsearch/src/main/java/org/elasticsearch/index/query/support/QueryParsers.java
@@ -21,7 +21,9 @@ package org.elasticsearch.index.query.support;
import org.apache.lucene.search.Filter;
import org.apache.lucene.search.FilteredQuery;
+import org.apache.lucene.search.MultiTermQuery;
import org.apache.lucene.search.Query;
+import org.elasticsearch.ElasticSearchIllegalArgumentException;
import org.elasticsearch.common.Nullable;
import org.elasticsearch.common.collect.ImmutableList;
import org.elasticsearch.common.lucene.search.AndFilter;
@@ -38,6 +40,41 @@ public final class QueryParsers {
}
+ public static MultiTermQuery.RewriteMethod parseRewriteMethod(@Nullable String rewriteMethod) {
+ if (rewriteMethod == null) {
+ return MultiTermQuery.CONSTANT_SCORE_AUTO_REWRITE_DEFAULT;
+ }
+ if ("constant_score_auto".equals(rewriteMethod) || "constant_score_auto".equals(rewriteMethod)) {
+ return MultiTermQuery.CONSTANT_SCORE_AUTO_REWRITE_DEFAULT;
+ }
+ if ("scoring_boolean".equals(rewriteMethod) || "scoringBoolean".equals(rewriteMethod)) {
+ return MultiTermQuery.SCORING_BOOLEAN_QUERY_REWRITE;
+ }
+ if ("constant_score_boolean".equals(rewriteMethod) || "constantScoreBoolean".equals(rewriteMethod)) {
+ return MultiTermQuery.CONSTANT_SCORE_BOOLEAN_QUERY_REWRITE;
+ }
+ if ("constant_score_filter".equals(rewriteMethod) || "constantScoreFilter".equals(rewriteMethod)) {
+ return MultiTermQuery.CONSTANT_SCORE_FILTER_REWRITE;
+ }
+ if (rewriteMethod.startsWith("top_terms_")) {
+ int size = Integer.parseInt(rewriteMethod.substring("top_terms_".length()));
+ return new MultiTermQuery.TopTermsScoringBooleanQueryRewrite(size);
+ }
+ if (rewriteMethod.startsWith("topTerms")) {
+ int size = Integer.parseInt(rewriteMethod.substring("topTerms".length()));
+ return new MultiTermQuery.TopTermsScoringBooleanQueryRewrite(size);
+ }
+ if (rewriteMethod.startsWith("top_terms_boost_")) {
+ int size = Integer.parseInt(rewriteMethod.substring("top_terms_boost_".length()));
+ return new MultiTermQuery.TopTermsBoostOnlyBooleanQueryRewrite(size);
+ }
+ if (rewriteMethod.startsWith("topTermsBoost")) {
+ int size = Integer.parseInt(rewriteMethod.substring("topTermsBoost".length()));
+ return new MultiTermQuery.TopTermsBoostOnlyBooleanQueryRewrite(size);
+ }
+ throw new ElasticSearchIllegalArgumentException("Failed to parse rewrite_method [" + rewriteMethod + "]");
+ }
+
public static Query wrapSmartNameQuery(Query query, @Nullable MapperService.SmartNameFieldMappers smartFieldMappers,
QueryParseContext parseContext) {
if (smartFieldMappers == null) {