mirror of
https://github.com/honeymoose/OpenSearch.git
synced 2025-02-17 10:25:15 +00:00
Allow to customize quote analyzer to be used when quoting text in a query_string, closes #1931.
This commit is contained in:
parent
379976b5ce
commit
acbd7b686a
@ -64,12 +64,17 @@ public class MapperQueryParser extends QueryParser {
|
|||||||
|
|
||||||
private final QueryParseContext parseContext;
|
private final QueryParseContext parseContext;
|
||||||
|
|
||||||
|
private Analyzer quoteAnalyzer;
|
||||||
|
|
||||||
private boolean forcedAnalyzer;
|
private boolean forcedAnalyzer;
|
||||||
|
private boolean forcedQuoteAnalyzer;
|
||||||
|
|
||||||
private FieldMapper currentMapper;
|
private FieldMapper currentMapper;
|
||||||
|
|
||||||
private boolean analyzeWildcard;
|
private boolean analyzeWildcard;
|
||||||
|
|
||||||
|
private String quoteFieldSuffix;
|
||||||
|
|
||||||
public MapperQueryParser(QueryParseContext parseContext) {
|
public MapperQueryParser(QueryParseContext parseContext) {
|
||||||
super(Lucene.QUERYPARSER_VERSION, null, null);
|
super(Lucene.QUERYPARSER_VERSION, null, null);
|
||||||
this.parseContext = parseContext;
|
this.parseContext = parseContext;
|
||||||
@ -85,6 +90,17 @@ public class MapperQueryParser extends QueryParser {
|
|||||||
this.field = settings.defaultField();
|
this.field = settings.defaultField();
|
||||||
this.forcedAnalyzer = settings.forcedAnalyzer() != null;
|
this.forcedAnalyzer = settings.forcedAnalyzer() != null;
|
||||||
this.analyzer = forcedAnalyzer ? settings.forcedAnalyzer() : settings.defaultAnalyzer();
|
this.analyzer = forcedAnalyzer ? settings.forcedAnalyzer() : settings.defaultAnalyzer();
|
||||||
|
if (settings.forcedQuoteAnalyzer() != null) {
|
||||||
|
this.forcedQuoteAnalyzer = true;
|
||||||
|
this.quoteAnalyzer = settings.forcedQuoteAnalyzer();
|
||||||
|
} else if (forcedAnalyzer) {
|
||||||
|
this.forcedQuoteAnalyzer = true;
|
||||||
|
this.quoteAnalyzer = settings.forcedAnalyzer();
|
||||||
|
} else {
|
||||||
|
this.forcedAnalyzer = false;
|
||||||
|
this.quoteAnalyzer = settings.defaultQuoteAnalyzer();
|
||||||
|
}
|
||||||
|
this.quoteFieldSuffix = settings.quoteFieldSuffix();
|
||||||
setMultiTermRewriteMethod(settings.rewriteMethod());
|
setMultiTermRewriteMethod(settings.rewriteMethod());
|
||||||
setEnablePositionIncrements(settings.enablePositionIncrements());
|
setEnablePositionIncrements(settings.enablePositionIncrements());
|
||||||
setAutoGeneratePhraseQueries(settings.autoGeneratePhraseQueries());
|
setAutoGeneratePhraseQueries(settings.autoGeneratePhraseQueries());
|
||||||
@ -122,10 +138,25 @@ public class MapperQueryParser extends QueryParser {
|
|||||||
currentMapper = null;
|
currentMapper = null;
|
||||||
Analyzer oldAnalyzer = analyzer;
|
Analyzer oldAnalyzer = analyzer;
|
||||||
try {
|
try {
|
||||||
MapperService.SmartNameFieldMappers fieldMappers = parseContext.smartFieldMappers(field);
|
MapperService.SmartNameFieldMappers fieldMappers = null;
|
||||||
|
if (quoted) {
|
||||||
|
analyzer = quoteAnalyzer;
|
||||||
|
if (quoteFieldSuffix != null) {
|
||||||
|
fieldMappers = parseContext.smartFieldMappers(field + quoteFieldSuffix);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (fieldMappers == null) {
|
||||||
|
fieldMappers = parseContext.smartFieldMappers(field);
|
||||||
|
}
|
||||||
if (fieldMappers != null) {
|
if (fieldMappers != null) {
|
||||||
if (!forcedAnalyzer) {
|
if (quoted) {
|
||||||
analyzer = fieldMappers.searchAnalyzer();
|
if (!forcedQuoteAnalyzer) {
|
||||||
|
analyzer = fieldMappers.searchQuoteAnalyzer();
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (!forcedAnalyzer) {
|
||||||
|
analyzer = fieldMappers.searchAnalyzer();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
currentMapper = fieldMappers.fieldMappers().mapper();
|
currentMapper = fieldMappers.fieldMappers().mapper();
|
||||||
if (currentMapper != null) {
|
if (currentMapper != null) {
|
||||||
|
@ -45,7 +45,10 @@ public class QueryParserSettings {
|
|||||||
private boolean analyzeWildcard = DEFAULT_ANALYZE_WILDCARD;
|
private boolean analyzeWildcard = DEFAULT_ANALYZE_WILDCARD;
|
||||||
private boolean escape = false;
|
private boolean escape = false;
|
||||||
private Analyzer defaultAnalyzer = null;
|
private Analyzer defaultAnalyzer = null;
|
||||||
|
private Analyzer defaultQuoteAnalyzer = null;
|
||||||
private Analyzer forcedAnalyzer = null;
|
private Analyzer forcedAnalyzer = null;
|
||||||
|
private Analyzer forcedQuoteAnalyzer = null;
|
||||||
|
private String quoteFieldSuffix = null;
|
||||||
private MultiTermQuery.RewriteMethod rewriteMethod = MultiTermQuery.CONSTANT_SCORE_AUTO_REWRITE_DEFAULT;
|
private MultiTermQuery.RewriteMethod rewriteMethod = MultiTermQuery.CONSTANT_SCORE_AUTO_REWRITE_DEFAULT;
|
||||||
private String minimumShouldMatch;
|
private String minimumShouldMatch;
|
||||||
|
|
||||||
@ -153,6 +156,14 @@ public class QueryParserSettings {
|
|||||||
this.defaultAnalyzer = defaultAnalyzer;
|
this.defaultAnalyzer = defaultAnalyzer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Analyzer defaultQuoteAnalyzer() {
|
||||||
|
return defaultQuoteAnalyzer;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void defaultQuoteAnalyzer(Analyzer defaultAnalyzer) {
|
||||||
|
this.defaultQuoteAnalyzer = defaultAnalyzer;
|
||||||
|
}
|
||||||
|
|
||||||
public Analyzer forcedAnalyzer() {
|
public Analyzer forcedAnalyzer() {
|
||||||
return forcedAnalyzer;
|
return forcedAnalyzer;
|
||||||
}
|
}
|
||||||
@ -161,6 +172,14 @@ public class QueryParserSettings {
|
|||||||
this.forcedAnalyzer = forcedAnalyzer;
|
this.forcedAnalyzer = forcedAnalyzer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Analyzer forcedQuoteAnalyzer() {
|
||||||
|
return forcedQuoteAnalyzer;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void forcedQuoteAnalyzer(Analyzer forcedAnalyzer) {
|
||||||
|
this.forcedQuoteAnalyzer = forcedAnalyzer;
|
||||||
|
}
|
||||||
|
|
||||||
public boolean analyzeWildcard() {
|
public boolean analyzeWildcard() {
|
||||||
return this.analyzeWildcard;
|
return this.analyzeWildcard;
|
||||||
}
|
}
|
||||||
@ -185,6 +204,14 @@ public class QueryParserSettings {
|
|||||||
this.minimumShouldMatch = minimumShouldMatch;
|
this.minimumShouldMatch = minimumShouldMatch;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void quoteFieldSuffix(String quoteFieldSuffix) {
|
||||||
|
this.quoteFieldSuffix = quoteFieldSuffix;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String quoteFieldSuffix() {
|
||||||
|
return this.quoteFieldSuffix;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (this == o) return true;
|
if (this == o) return true;
|
||||||
@ -204,8 +231,12 @@ public class QueryParserSettings {
|
|||||||
if (phraseSlop != that.phraseSlop) return false;
|
if (phraseSlop != that.phraseSlop) return false;
|
||||||
if (defaultAnalyzer != null ? !defaultAnalyzer.equals(that.defaultAnalyzer) : that.defaultAnalyzer != null)
|
if (defaultAnalyzer != null ? !defaultAnalyzer.equals(that.defaultAnalyzer) : that.defaultAnalyzer != null)
|
||||||
return false;
|
return false;
|
||||||
|
if (defaultQuoteAnalyzer != null ? !defaultQuoteAnalyzer.equals(that.defaultQuoteAnalyzer) : that.defaultQuoteAnalyzer != null)
|
||||||
|
return false;
|
||||||
if (forcedAnalyzer != null ? !forcedAnalyzer.equals(that.forcedAnalyzer) : that.forcedAnalyzer != null)
|
if (forcedAnalyzer != null ? !forcedAnalyzer.equals(that.forcedAnalyzer) : that.forcedAnalyzer != null)
|
||||||
return false;
|
return false;
|
||||||
|
if (forcedQuoteAnalyzer != null ? !forcedQuoteAnalyzer.equals(that.forcedQuoteAnalyzer) : that.forcedQuoteAnalyzer != null)
|
||||||
|
return false;
|
||||||
if (defaultField != null ? !defaultField.equals(that.defaultField) : that.defaultField != null) return false;
|
if (defaultField != null ? !defaultField.equals(that.defaultField) : that.defaultField != null) return false;
|
||||||
if (defaultOperator != that.defaultOperator) return false;
|
if (defaultOperator != that.defaultOperator) return false;
|
||||||
if (queryString != null ? !queryString.equals(that.queryString) : that.queryString != null) return false;
|
if (queryString != null ? !queryString.equals(that.queryString) : that.queryString != null) return false;
|
||||||
@ -213,6 +244,8 @@ public class QueryParserSettings {
|
|||||||
return false;
|
return false;
|
||||||
if (minimumShouldMatch != null ? !minimumShouldMatch.equals(that.minimumShouldMatch) : that.minimumShouldMatch != null)
|
if (minimumShouldMatch != null ? !minimumShouldMatch.equals(that.minimumShouldMatch) : that.minimumShouldMatch != null)
|
||||||
return false;
|
return false;
|
||||||
|
if (quoteFieldSuffix != null ? !quoteFieldSuffix.equals(that.quoteFieldSuffix) : that.quoteFieldSuffix != null)
|
||||||
|
return false;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -232,7 +265,9 @@ public class QueryParserSettings {
|
|||||||
result = 31 * result + fuzzyPrefixLength;
|
result = 31 * result + fuzzyPrefixLength;
|
||||||
result = 31 * result + (escape ? 1 : 0);
|
result = 31 * result + (escape ? 1 : 0);
|
||||||
result = 31 * result + (defaultAnalyzer != null ? defaultAnalyzer.hashCode() : 0);
|
result = 31 * result + (defaultAnalyzer != null ? defaultAnalyzer.hashCode() : 0);
|
||||||
|
result = 31 * result + (defaultQuoteAnalyzer != null ? defaultQuoteAnalyzer.hashCode() : 0);
|
||||||
result = 31 * result + (forcedAnalyzer != null ? forcedAnalyzer.hashCode() : 0);
|
result = 31 * result + (forcedAnalyzer != null ? forcedAnalyzer.hashCode() : 0);
|
||||||
|
result = 31 * result + (forcedQuoteAnalyzer != null ? forcedQuoteAnalyzer.hashCode() : 0);
|
||||||
result = 31 * result + (analyzeWildcard ? 1 : 0);
|
result = 31 * result + (analyzeWildcard ? 1 : 0);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -51,6 +51,7 @@ public class AnalysisService extends AbstractIndexComponent implements Closeable
|
|||||||
private final NamedAnalyzer defaultAnalyzer;
|
private final NamedAnalyzer defaultAnalyzer;
|
||||||
private final NamedAnalyzer defaultIndexAnalyzer;
|
private final NamedAnalyzer defaultIndexAnalyzer;
|
||||||
private final NamedAnalyzer defaultSearchAnalyzer;
|
private final NamedAnalyzer defaultSearchAnalyzer;
|
||||||
|
private final NamedAnalyzer defaultSearchQuoteAnalyzer;
|
||||||
|
|
||||||
public AnalysisService(Index index) {
|
public AnalysisService(Index index) {
|
||||||
this(index, ImmutableSettings.Builder.EMPTY_SETTINGS, null, null, null, null, null);
|
this(index, ImmutableSettings.Builder.EMPTY_SETTINGS, null, null, null, null, null);
|
||||||
@ -209,6 +210,9 @@ public class AnalysisService extends AbstractIndexComponent implements Closeable
|
|||||||
if (!analyzerProviders.containsKey("default_search")) {
|
if (!analyzerProviders.containsKey("default_search")) {
|
||||||
analyzerProviders.put("default_search", analyzerProviders.get("default"));
|
analyzerProviders.put("default_search", analyzerProviders.get("default"));
|
||||||
}
|
}
|
||||||
|
if (!analyzerProviders.containsKey("default_search_quoted")) {
|
||||||
|
analyzerProviders.put("default_search_quoted", analyzerProviders.get("default_search"));
|
||||||
|
}
|
||||||
|
|
||||||
Map<String, NamedAnalyzer> analyzers = newHashMap();
|
Map<String, NamedAnalyzer> analyzers = newHashMap();
|
||||||
for (AnalyzerProvider analyzerFactory : analyzerProviders.values()) {
|
for (AnalyzerProvider analyzerFactory : analyzerProviders.values()) {
|
||||||
@ -233,6 +237,7 @@ public class AnalysisService extends AbstractIndexComponent implements Closeable
|
|||||||
defaultAnalyzer = analyzers.get("default");
|
defaultAnalyzer = analyzers.get("default");
|
||||||
defaultIndexAnalyzer = analyzers.containsKey("default_index") ? analyzers.get("default_index") : analyzers.get("default");
|
defaultIndexAnalyzer = analyzers.containsKey("default_index") ? analyzers.get("default_index") : analyzers.get("default");
|
||||||
defaultSearchAnalyzer = analyzers.containsKey("default_search") ? analyzers.get("default_search") : analyzers.get("default");
|
defaultSearchAnalyzer = analyzers.containsKey("default_search") ? analyzers.get("default_search") : analyzers.get("default");
|
||||||
|
defaultSearchQuoteAnalyzer = analyzers.containsKey("default_search_quote") ? analyzers.get("default_search_quote") : defaultSearchAnalyzer;
|
||||||
|
|
||||||
this.analyzers = ImmutableMap.copyOf(analyzers);
|
this.analyzers = ImmutableMap.copyOf(analyzers);
|
||||||
}
|
}
|
||||||
@ -268,6 +273,10 @@ public class AnalysisService extends AbstractIndexComponent implements Closeable
|
|||||||
return defaultSearchAnalyzer;
|
return defaultSearchAnalyzer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public NamedAnalyzer defaultSearchQuoteAnalyzer() {
|
||||||
|
return defaultSearchQuoteAnalyzer;
|
||||||
|
}
|
||||||
|
|
||||||
public TokenizerFactory tokenizer(String name) {
|
public TokenizerFactory tokenizer(String name) {
|
||||||
return tokenizers.get(name);
|
return tokenizers.get(name);
|
||||||
}
|
}
|
||||||
|
@ -42,6 +42,7 @@ public class DocumentFieldMappers implements Iterable<FieldMapper> {
|
|||||||
|
|
||||||
private final FieldNameAnalyzer indexAnalyzer;
|
private final FieldNameAnalyzer indexAnalyzer;
|
||||||
private final FieldNameAnalyzer searchAnalyzer;
|
private final FieldNameAnalyzer searchAnalyzer;
|
||||||
|
private final FieldNameAnalyzer searchQuoteAnalyzer;
|
||||||
|
|
||||||
public DocumentFieldMappers(DocumentMapper docMapper, Iterable<FieldMapper> fieldMappers) {
|
public DocumentFieldMappers(DocumentMapper docMapper, Iterable<FieldMapper> fieldMappers) {
|
||||||
final Map<String, FieldMappers> tempNameFieldMappers = newHashMap();
|
final Map<String, FieldMappers> tempNameFieldMappers = newHashMap();
|
||||||
@ -50,6 +51,7 @@ public class DocumentFieldMappers implements Iterable<FieldMapper> {
|
|||||||
|
|
||||||
final Map<String, Analyzer> indexAnalyzers = newHashMap();
|
final Map<String, Analyzer> indexAnalyzers = newHashMap();
|
||||||
final Map<String, Analyzer> searchAnalyzers = newHashMap();
|
final Map<String, Analyzer> searchAnalyzers = newHashMap();
|
||||||
|
final Map<String, Analyzer> searchQuoteAnalyzers = newHashMap();
|
||||||
|
|
||||||
for (FieldMapper fieldMapper : fieldMappers) {
|
for (FieldMapper fieldMapper : fieldMappers) {
|
||||||
FieldMappers mappers = tempNameFieldMappers.get(fieldMapper.names().name());
|
FieldMappers mappers = tempNameFieldMappers.get(fieldMapper.names().name());
|
||||||
@ -82,6 +84,9 @@ public class DocumentFieldMappers implements Iterable<FieldMapper> {
|
|||||||
if (fieldMapper.searchAnalyzer() != null) {
|
if (fieldMapper.searchAnalyzer() != null) {
|
||||||
searchAnalyzers.put(fieldMapper.names().indexName(), fieldMapper.searchAnalyzer());
|
searchAnalyzers.put(fieldMapper.names().indexName(), fieldMapper.searchAnalyzer());
|
||||||
}
|
}
|
||||||
|
if (fieldMapper.searchQuoteAnalyzer() != null) {
|
||||||
|
searchQuoteAnalyzers.put(fieldMapper.names().indexName(), fieldMapper.searchQuoteAnalyzer());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
this.fieldMappers = ImmutableList.copyOf(fieldMappers);
|
this.fieldMappers = ImmutableList.copyOf(fieldMappers);
|
||||||
this.nameFieldMappers = ImmutableMap.copyOf(tempNameFieldMappers);
|
this.nameFieldMappers = ImmutableMap.copyOf(tempNameFieldMappers);
|
||||||
@ -90,6 +95,7 @@ public class DocumentFieldMappers implements Iterable<FieldMapper> {
|
|||||||
|
|
||||||
this.indexAnalyzer = new FieldNameAnalyzer(indexAnalyzers, docMapper.indexAnalyzer());
|
this.indexAnalyzer = new FieldNameAnalyzer(indexAnalyzers, docMapper.indexAnalyzer());
|
||||||
this.searchAnalyzer = new FieldNameAnalyzer(searchAnalyzers, docMapper.searchAnalyzer());
|
this.searchAnalyzer = new FieldNameAnalyzer(searchAnalyzers, docMapper.searchAnalyzer());
|
||||||
|
this.searchQuoteAnalyzer = new FieldNameAnalyzer(searchQuoteAnalyzers, docMapper.searchQuotedAnalyzer());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -179,6 +185,10 @@ public class DocumentFieldMappers implements Iterable<FieldMapper> {
|
|||||||
return this.searchAnalyzer;
|
return this.searchAnalyzer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Analyzer searchQuoteAnalyzer() {
|
||||||
|
return this.searchQuoteAnalyzer;
|
||||||
|
}
|
||||||
|
|
||||||
public DocumentFieldMappers concat(DocumentMapper docMapper, FieldMapper... fieldMappers) {
|
public DocumentFieldMappers concat(DocumentMapper docMapper, FieldMapper... fieldMappers) {
|
||||||
return concat(docMapper, newArrayList(fieldMappers));
|
return concat(docMapper, newArrayList(fieldMappers));
|
||||||
}
|
}
|
||||||
|
@ -132,6 +132,8 @@ public class DocumentMapper implements ToXContent {
|
|||||||
|
|
||||||
private NamedAnalyzer searchAnalyzer;
|
private NamedAnalyzer searchAnalyzer;
|
||||||
|
|
||||||
|
private NamedAnalyzer searchQuoteAnalyzer;
|
||||||
|
|
||||||
private final String index;
|
private final String index;
|
||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
@ -193,6 +195,14 @@ public class DocumentMapper implements ToXContent {
|
|||||||
|
|
||||||
public Builder searchAnalyzer(NamedAnalyzer searchAnalyzer) {
|
public Builder searchAnalyzer(NamedAnalyzer searchAnalyzer) {
|
||||||
this.searchAnalyzer = searchAnalyzer;
|
this.searchAnalyzer = searchAnalyzer;
|
||||||
|
if (this.searchQuoteAnalyzer == null) {
|
||||||
|
this.searchQuoteAnalyzer = searchAnalyzer;
|
||||||
|
}
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Builder searchQuoteAnalyzer(NamedAnalyzer searchQuoteAnalyzer) {
|
||||||
|
this.searchQuoteAnalyzer = searchQuoteAnalyzer;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -200,10 +210,14 @@ public class DocumentMapper implements ToXContent {
|
|||||||
return searchAnalyzer != null;
|
return searchAnalyzer != null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean hasSearchQuoteAnalyzer() {
|
||||||
|
return searchQuoteAnalyzer != null;
|
||||||
|
}
|
||||||
|
|
||||||
public DocumentMapper build(DocumentMapperParser docMapperParser) {
|
public DocumentMapper build(DocumentMapperParser docMapperParser) {
|
||||||
Preconditions.checkNotNull(rootObjectMapper, "Mapper builder must have the root object mapper set");
|
Preconditions.checkNotNull(rootObjectMapper, "Mapper builder must have the root object mapper set");
|
||||||
return new DocumentMapper(index, indexSettings, docMapperParser, rootObjectMapper, meta,
|
return new DocumentMapper(index, indexSettings, docMapperParser, rootObjectMapper, meta,
|
||||||
indexAnalyzer, searchAnalyzer,
|
indexAnalyzer, searchAnalyzer, searchQuoteAnalyzer,
|
||||||
rootMappers);
|
rootMappers);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -237,6 +251,7 @@ public class DocumentMapper implements ToXContent {
|
|||||||
private final NamedAnalyzer indexAnalyzer;
|
private final NamedAnalyzer indexAnalyzer;
|
||||||
|
|
||||||
private final NamedAnalyzer searchAnalyzer;
|
private final NamedAnalyzer searchAnalyzer;
|
||||||
|
private final NamedAnalyzer searchQuoteAnalyzer;
|
||||||
|
|
||||||
private volatile DocumentFieldMappers fieldMappers;
|
private volatile DocumentFieldMappers fieldMappers;
|
||||||
|
|
||||||
@ -257,7 +272,7 @@ public class DocumentMapper implements ToXContent {
|
|||||||
public DocumentMapper(String index, @Nullable Settings indexSettings, DocumentMapperParser docMapperParser,
|
public DocumentMapper(String index, @Nullable Settings indexSettings, DocumentMapperParser docMapperParser,
|
||||||
RootObjectMapper rootObjectMapper,
|
RootObjectMapper rootObjectMapper,
|
||||||
ImmutableMap<String, Object> meta,
|
ImmutableMap<String, Object> meta,
|
||||||
NamedAnalyzer indexAnalyzer, NamedAnalyzer searchAnalyzer,
|
NamedAnalyzer indexAnalyzer, NamedAnalyzer searchAnalyzer, NamedAnalyzer searchQuoteAnalyzer,
|
||||||
Map<Class<? extends RootMapper>, RootMapper> rootMappers) {
|
Map<Class<? extends RootMapper>, RootMapper> rootMappers) {
|
||||||
this.index = index;
|
this.index = index;
|
||||||
this.indexSettings = indexSettings;
|
this.indexSettings = indexSettings;
|
||||||
@ -278,6 +293,7 @@ public class DocumentMapper implements ToXContent {
|
|||||||
|
|
||||||
this.indexAnalyzer = indexAnalyzer;
|
this.indexAnalyzer = indexAnalyzer;
|
||||||
this.searchAnalyzer = searchAnalyzer;
|
this.searchAnalyzer = searchAnalyzer;
|
||||||
|
this.searchQuoteAnalyzer = searchQuoteAnalyzer != null ? searchQuoteAnalyzer : searchAnalyzer;
|
||||||
|
|
||||||
this.typeFilter = typeMapper().fieldFilter(type, null);
|
this.typeFilter = typeMapper().fieldFilter(type, null);
|
||||||
|
|
||||||
@ -389,6 +405,10 @@ public class DocumentMapper implements ToXContent {
|
|||||||
return this.searchAnalyzer;
|
return this.searchAnalyzer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Analyzer searchQuotedAnalyzer() {
|
||||||
|
return this.searchQuoteAnalyzer;
|
||||||
|
}
|
||||||
|
|
||||||
public Filter typeFilter() {
|
public Filter typeFilter() {
|
||||||
return this.typeFilter;
|
return this.typeFilter;
|
||||||
}
|
}
|
||||||
|
@ -177,6 +177,12 @@ public class DocumentMapperParser extends AbstractIndexComponent {
|
|||||||
throw new MapperParsingException("Analyzer [" + fieldNode.toString() + "] not found for search_analyzer setting on root type [" + type + "]");
|
throw new MapperParsingException("Analyzer [" + fieldNode.toString() + "] not found for search_analyzer setting on root type [" + type + "]");
|
||||||
}
|
}
|
||||||
docBuilder.searchAnalyzer(analyzer);
|
docBuilder.searchAnalyzer(analyzer);
|
||||||
|
} else if ("search_quote_analyzer".equals(fieldName)) {
|
||||||
|
NamedAnalyzer analyzer = analysisService.analyzer(fieldNode.toString());
|
||||||
|
if (analyzer == null) {
|
||||||
|
throw new MapperParsingException("Analyzer [" + fieldNode.toString() + "] not found for search_analyzer setting on root type [" + type + "]");
|
||||||
|
}
|
||||||
|
docBuilder.searchQuoteAnalyzer(analyzer);
|
||||||
} else if ("analyzer".equals(fieldName)) {
|
} else if ("analyzer".equals(fieldName)) {
|
||||||
NamedAnalyzer analyzer = analysisService.analyzer(fieldNode.toString());
|
NamedAnalyzer analyzer = analysisService.analyzer(fieldNode.toString());
|
||||||
if (analyzer == null) {
|
if (analyzer == null) {
|
||||||
@ -198,6 +204,9 @@ public class DocumentMapperParser extends AbstractIndexComponent {
|
|||||||
if (!docBuilder.hasSearchAnalyzer()) {
|
if (!docBuilder.hasSearchAnalyzer()) {
|
||||||
docBuilder.searchAnalyzer(analysisService.defaultSearchAnalyzer());
|
docBuilder.searchAnalyzer(analysisService.defaultSearchAnalyzer());
|
||||||
}
|
}
|
||||||
|
if (!docBuilder.hasSearchQuoteAnalyzer()) {
|
||||||
|
docBuilder.searchAnalyzer(analysisService.defaultSearchQuoteAnalyzer());
|
||||||
|
}
|
||||||
|
|
||||||
ImmutableMap<String, Object> attributes = ImmutableMap.of();
|
ImmutableMap<String, Object> attributes = ImmutableMap.of();
|
||||||
if (mapping.containsKey("_meta")) {
|
if (mapping.containsKey("_meta")) {
|
||||||
|
@ -147,6 +147,11 @@ public interface FieldMapper<T> {
|
|||||||
*/
|
*/
|
||||||
Analyzer searchAnalyzer();
|
Analyzer searchAnalyzer();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The analyzer that will be used for quoted search on the field.
|
||||||
|
*/
|
||||||
|
Analyzer searchQuoteAnalyzer();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the value that will be used as a result for search. Can be only of specific types... .
|
* Returns the value that will be used as a result for search. Can be only of specific types... .
|
||||||
*/
|
*/
|
||||||
|
@ -95,6 +95,7 @@ public class MapperService extends AbstractIndexComponent implements Iterable<Do
|
|||||||
private final InternalObjectMapperListener objectMapperListener = new InternalObjectMapperListener();
|
private final InternalObjectMapperListener objectMapperListener = new InternalObjectMapperListener();
|
||||||
|
|
||||||
private final SmartIndexNameSearchAnalyzer searchAnalyzer;
|
private final SmartIndexNameSearchAnalyzer searchAnalyzer;
|
||||||
|
private final SmartIndexNameSearchQuoteAnalyzer searchQuoteAnalyzer;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
public MapperService(Index index, @IndexSettings Settings indexSettings, Environment environment, AnalysisService analysisService) {
|
public MapperService(Index index, @IndexSettings Settings indexSettings, Environment environment, AnalysisService analysisService) {
|
||||||
@ -102,6 +103,7 @@ public class MapperService extends AbstractIndexComponent implements Iterable<Do
|
|||||||
this.analysisService = analysisService;
|
this.analysisService = analysisService;
|
||||||
this.documentParser = new DocumentMapperParser(index, indexSettings, analysisService);
|
this.documentParser = new DocumentMapperParser(index, indexSettings, analysisService);
|
||||||
this.searchAnalyzer = new SmartIndexNameSearchAnalyzer(analysisService.defaultSearchAnalyzer());
|
this.searchAnalyzer = new SmartIndexNameSearchAnalyzer(analysisService.defaultSearchAnalyzer());
|
||||||
|
this.searchQuoteAnalyzer = new SmartIndexNameSearchQuoteAnalyzer(analysisService.defaultSearchQuoteAnalyzer());
|
||||||
|
|
||||||
this.dynamic = componentSettings.getAsBoolean("dynamic", true);
|
this.dynamic = componentSettings.getAsBoolean("dynamic", true);
|
||||||
String defaultMappingLocation = componentSettings.get("default_mapping_location");
|
String defaultMappingLocation = componentSettings.get("default_mapping_location");
|
||||||
@ -665,6 +667,10 @@ public class MapperService extends AbstractIndexComponent implements Iterable<Do
|
|||||||
return this.searchAnalyzer;
|
return this.searchAnalyzer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Analyzer searchQuoteAnalyzer() {
|
||||||
|
return this.searchQuoteAnalyzer;
|
||||||
|
}
|
||||||
|
|
||||||
public static class SmartNameObjectMapper {
|
public static class SmartNameObjectMapper {
|
||||||
private final ObjectMapper mapper;
|
private final ObjectMapper mapper;
|
||||||
private final DocumentMapper docMapper;
|
private final DocumentMapper docMapper;
|
||||||
@ -767,6 +773,19 @@ public class MapperService extends AbstractIndexComponent implements Iterable<Do
|
|||||||
}
|
}
|
||||||
return mapperService.searchAnalyzer();
|
return mapperService.searchAnalyzer();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Analyzer searchQuoteAnalyzer() {
|
||||||
|
if (hasMapper()) {
|
||||||
|
Analyzer analyzer = mapper().searchQuoteAnalyzer();
|
||||||
|
if (analyzer != null) {
|
||||||
|
return analyzer;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (docMapper != null && docMapper.searchQuotedAnalyzer() != null) {
|
||||||
|
return docMapper.searchQuotedAnalyzer();
|
||||||
|
}
|
||||||
|
return mapperService.searchQuoteAnalyzer();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
final class SmartIndexNameSearchAnalyzer extends Analyzer {
|
final class SmartIndexNameSearchAnalyzer extends Analyzer {
|
||||||
@ -867,6 +886,104 @@ public class MapperService extends AbstractIndexComponent implements Iterable<Do
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
final class SmartIndexNameSearchQuoteAnalyzer extends Analyzer {
|
||||||
|
|
||||||
|
private final Analyzer defaultAnalyzer;
|
||||||
|
|
||||||
|
SmartIndexNameSearchQuoteAnalyzer(Analyzer defaultAnalyzer) {
|
||||||
|
this.defaultAnalyzer = defaultAnalyzer;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getPositionIncrementGap(String fieldName) {
|
||||||
|
int dotIndex = fieldName.indexOf('.');
|
||||||
|
if (dotIndex != -1) {
|
||||||
|
String possibleType = fieldName.substring(0, dotIndex);
|
||||||
|
DocumentMapper possibleDocMapper = mappers.get(possibleType);
|
||||||
|
if (possibleDocMapper != null) {
|
||||||
|
return possibleDocMapper.mappers().searchQuoteAnalyzer().getPositionIncrementGap(fieldName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
FieldMappers mappers = fullNameFieldMappers.get(fieldName);
|
||||||
|
if (mappers != null && mappers.mapper() != null && mappers.mapper().searchAnalyzer() != null) {
|
||||||
|
return mappers.mapper().searchQuoteAnalyzer().getPositionIncrementGap(fieldName);
|
||||||
|
}
|
||||||
|
|
||||||
|
mappers = indexNameFieldMappers.get(fieldName);
|
||||||
|
if (mappers != null && mappers.mapper() != null && mappers.mapper().searchAnalyzer() != null) {
|
||||||
|
return mappers.mapper().searchQuoteAnalyzer().getPositionIncrementGap(fieldName);
|
||||||
|
}
|
||||||
|
return defaultAnalyzer.getPositionIncrementGap(fieldName);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getOffsetGap(Fieldable field) {
|
||||||
|
String fieldName = field.name();
|
||||||
|
int dotIndex = fieldName.indexOf('.');
|
||||||
|
if (dotIndex != -1) {
|
||||||
|
String possibleType = fieldName.substring(0, dotIndex);
|
||||||
|
DocumentMapper possibleDocMapper = mappers.get(possibleType);
|
||||||
|
if (possibleDocMapper != null) {
|
||||||
|
return possibleDocMapper.mappers().searchQuoteAnalyzer().getOffsetGap(field);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
FieldMappers mappers = fullNameFieldMappers.get(fieldName);
|
||||||
|
if (mappers != null && mappers.mapper() != null && mappers.mapper().searchAnalyzer() != null) {
|
||||||
|
return mappers.mapper().searchQuoteAnalyzer().getOffsetGap(field);
|
||||||
|
}
|
||||||
|
|
||||||
|
mappers = indexNameFieldMappers.get(fieldName);
|
||||||
|
if (mappers != null && mappers.mapper() != null && mappers.mapper().searchAnalyzer() != null) {
|
||||||
|
return mappers.mapper().searchQuoteAnalyzer().getOffsetGap(field);
|
||||||
|
}
|
||||||
|
return defaultAnalyzer.getOffsetGap(field);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public final TokenStream tokenStream(String fieldName, Reader reader) {
|
||||||
|
int dotIndex = fieldName.indexOf('.');
|
||||||
|
if (dotIndex != -1) {
|
||||||
|
String possibleType = fieldName.substring(0, dotIndex);
|
||||||
|
DocumentMapper possibleDocMapper = mappers.get(possibleType);
|
||||||
|
if (possibleDocMapper != null) {
|
||||||
|
return possibleDocMapper.mappers().searchQuoteAnalyzer().tokenStream(fieldName, reader);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
FieldMappers mappers = fullNameFieldMappers.get(fieldName);
|
||||||
|
if (mappers != null && mappers.mapper() != null && mappers.mapper().searchAnalyzer() != null) {
|
||||||
|
return mappers.mapper().searchQuoteAnalyzer().tokenStream(fieldName, reader);
|
||||||
|
}
|
||||||
|
|
||||||
|
mappers = indexNameFieldMappers.get(fieldName);
|
||||||
|
if (mappers != null && mappers.mapper() != null && mappers.mapper().searchAnalyzer() != null) {
|
||||||
|
return mappers.mapper().searchQuoteAnalyzer().tokenStream(fieldName, reader);
|
||||||
|
}
|
||||||
|
return defaultAnalyzer.tokenStream(fieldName, reader);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public final TokenStream reusableTokenStream(String fieldName, Reader reader) throws IOException {
|
||||||
|
int dotIndex = fieldName.indexOf('.');
|
||||||
|
if (dotIndex != -1) {
|
||||||
|
String possibleType = fieldName.substring(0, dotIndex);
|
||||||
|
DocumentMapper possibleDocMapper = mappers.get(possibleType);
|
||||||
|
if (possibleDocMapper != null) {
|
||||||
|
return possibleDocMapper.mappers().searchQuoteAnalyzer().reusableTokenStream(fieldName, reader);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
FieldMappers mappers = fullNameFieldMappers.get(fieldName);
|
||||||
|
if (mappers != null && mappers.mapper() != null && mappers.mapper().searchAnalyzer() != null) {
|
||||||
|
return mappers.mapper().searchQuoteAnalyzer().reusableTokenStream(fieldName, reader);
|
||||||
|
}
|
||||||
|
|
||||||
|
mappers = indexNameFieldMappers.get(fieldName);
|
||||||
|
if (mappers != null && mappers.mapper() != null && mappers.mapper().searchAnalyzer() != null) {
|
||||||
|
return mappers.mapper().searchQuoteAnalyzer().reusableTokenStream(fieldName, reader);
|
||||||
|
}
|
||||||
|
return defaultAnalyzer.reusableTokenStream(fieldName, reader);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
class InternalFieldMapperListener implements FieldMapperListener {
|
class InternalFieldMapperListener implements FieldMapperListener {
|
||||||
@Override
|
@Override
|
||||||
public void fieldMapper(FieldMapper fieldMapper) {
|
public void fieldMapper(FieldMapper fieldMapper) {
|
||||||
|
@ -301,6 +301,11 @@ public abstract class AbstractFieldMapper<T> implements FieldMapper<T>, Mapper {
|
|||||||
return this.searchAnalyzer;
|
return this.searchAnalyzer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Analyzer searchQuoteAnalyzer() {
|
||||||
|
return this.searchAnalyzer;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void parse(ParseContext context) throws IOException {
|
public void parse(ParseContext context) throws IOException {
|
||||||
try {
|
try {
|
||||||
|
@ -19,6 +19,7 @@
|
|||||||
|
|
||||||
package org.elasticsearch.index.mapper.core;
|
package org.elasticsearch.index.mapper.core;
|
||||||
|
|
||||||
|
import org.apache.lucene.analysis.Analyzer;
|
||||||
import org.apache.lucene.document.Field;
|
import org.apache.lucene.document.Field;
|
||||||
import org.apache.lucene.document.Fieldable;
|
import org.apache.lucene.document.Fieldable;
|
||||||
import org.elasticsearch.common.Strings;
|
import org.elasticsearch.common.Strings;
|
||||||
@ -55,6 +56,8 @@ public class StringFieldMapper extends AbstractFieldMapper<String> implements Al
|
|||||||
|
|
||||||
protected int positionOffsetGap = Defaults.POSITION_OFFSET_GAP;
|
protected int positionOffsetGap = Defaults.POSITION_OFFSET_GAP;
|
||||||
|
|
||||||
|
protected NamedAnalyzer searchQuotedAnalyzer;
|
||||||
|
|
||||||
public Builder(String name) {
|
public Builder(String name) {
|
||||||
super(name);
|
super(name);
|
||||||
builder = this;
|
builder = this;
|
||||||
@ -71,20 +74,35 @@ public class StringFieldMapper extends AbstractFieldMapper<String> implements Al
|
|||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Builder searchAnalyzer(NamedAnalyzer searchAnalyzer) {
|
||||||
|
super.searchAnalyzer(searchAnalyzer);
|
||||||
|
if (searchQuotedAnalyzer == null) {
|
||||||
|
searchQuotedAnalyzer = searchAnalyzer;
|
||||||
|
}
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
public Builder positionOffsetGap(int positionOffsetGap) {
|
public Builder positionOffsetGap(int positionOffsetGap) {
|
||||||
this.positionOffsetGap = positionOffsetGap;
|
this.positionOffsetGap = positionOffsetGap;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Builder searchQuotedAnalyzer(NamedAnalyzer analyzer) {
|
||||||
|
this.searchQuotedAnalyzer = analyzer;
|
||||||
|
return builder;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public StringFieldMapper build(BuilderContext context) {
|
public StringFieldMapper build(BuilderContext context) {
|
||||||
if (positionOffsetGap > 0) {
|
if (positionOffsetGap > 0) {
|
||||||
indexAnalyzer = new NamedCustomAnalyzer(indexAnalyzer, positionOffsetGap);
|
indexAnalyzer = new NamedCustomAnalyzer(indexAnalyzer, positionOffsetGap);
|
||||||
searchAnalyzer = new NamedCustomAnalyzer(searchAnalyzer, positionOffsetGap);
|
searchAnalyzer = new NamedCustomAnalyzer(searchAnalyzer, positionOffsetGap);
|
||||||
|
searchQuotedAnalyzer = new NamedCustomAnalyzer(searchQuotedAnalyzer, positionOffsetGap);
|
||||||
}
|
}
|
||||||
StringFieldMapper fieldMapper = new StringFieldMapper(buildNames(context),
|
StringFieldMapper fieldMapper = new StringFieldMapper(buildNames(context),
|
||||||
index, store, termVector, boost, omitNorms, omitTermFreqAndPositions, nullValue,
|
index, store, termVector, boost, omitNorms, omitTermFreqAndPositions, nullValue,
|
||||||
indexAnalyzer, searchAnalyzer, positionOffsetGap);
|
indexAnalyzer, searchAnalyzer, searchQuotedAnalyzer, positionOffsetGap);
|
||||||
fieldMapper.includeInAll(includeInAll);
|
fieldMapper.includeInAll(includeInAll);
|
||||||
return fieldMapper;
|
return fieldMapper;
|
||||||
}
|
}
|
||||||
@ -100,6 +118,12 @@ public class StringFieldMapper extends AbstractFieldMapper<String> implements Al
|
|||||||
Object propNode = entry.getValue();
|
Object propNode = entry.getValue();
|
||||||
if (propName.equals("null_value")) {
|
if (propName.equals("null_value")) {
|
||||||
builder.nullValue(propNode.toString());
|
builder.nullValue(propNode.toString());
|
||||||
|
} else if (propName.equals("search_quote_analyzer")) {
|
||||||
|
NamedAnalyzer analyzer = parserContext.analysisService().analyzer(propNode.toString());
|
||||||
|
if (analyzer == null) {
|
||||||
|
throw new MapperParsingException("Analyzer [" + propNode.toString() + "] not found for field [" + name + "]");
|
||||||
|
}
|
||||||
|
builder.searchQuotedAnalyzer(analyzer);
|
||||||
} else if (propName.equals("position_offset_gap")) {
|
} else if (propName.equals("position_offset_gap")) {
|
||||||
builder.positionOffsetGap(XContentMapValues.nodeIntegerValue(propNode, -1));
|
builder.positionOffsetGap(XContentMapValues.nodeIntegerValue(propNode, -1));
|
||||||
// we need to update to actual analyzers if they are not set in this case...
|
// we need to update to actual analyzers if they are not set in this case...
|
||||||
@ -110,6 +134,9 @@ public class StringFieldMapper extends AbstractFieldMapper<String> implements Al
|
|||||||
if (builder.searchAnalyzer == null) {
|
if (builder.searchAnalyzer == null) {
|
||||||
builder.searchAnalyzer = parserContext.analysisService().defaultSearchAnalyzer();
|
builder.searchAnalyzer = parserContext.analysisService().defaultSearchAnalyzer();
|
||||||
}
|
}
|
||||||
|
if (builder.searchQuotedAnalyzer == null) {
|
||||||
|
builder.searchQuotedAnalyzer = parserContext.analysisService().defaultSearchQuoteAnalyzer();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return builder;
|
return builder;
|
||||||
@ -122,18 +149,21 @@ public class StringFieldMapper extends AbstractFieldMapper<String> implements Al
|
|||||||
|
|
||||||
private int positionOffsetGap;
|
private int positionOffsetGap;
|
||||||
|
|
||||||
|
private NamedAnalyzer searchQuotedAnalyzer;
|
||||||
|
|
||||||
protected StringFieldMapper(Names names, Field.Index index, Field.Store store, Field.TermVector termVector,
|
protected StringFieldMapper(Names names, Field.Index index, Field.Store store, Field.TermVector termVector,
|
||||||
float boost, boolean omitNorms, boolean omitTermFreqAndPositions,
|
float boost, boolean omitNorms, boolean omitTermFreqAndPositions,
|
||||||
String nullValue, NamedAnalyzer indexAnalyzer, NamedAnalyzer searchAnalyzer) {
|
String nullValue, NamedAnalyzer indexAnalyzer, NamedAnalyzer searchAnalyzer) {
|
||||||
this(names, index, store, termVector, boost, omitNorms, omitTermFreqAndPositions, nullValue, indexAnalyzer, searchAnalyzer, Defaults.POSITION_OFFSET_GAP);
|
this(names, index, store, termVector, boost, omitNorms, omitTermFreqAndPositions, nullValue, indexAnalyzer, searchAnalyzer, searchAnalyzer, Defaults.POSITION_OFFSET_GAP);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected StringFieldMapper(Names names, Field.Index index, Field.Store store, Field.TermVector termVector,
|
protected StringFieldMapper(Names names, Field.Index index, Field.Store store, Field.TermVector termVector,
|
||||||
float boost, boolean omitNorms, boolean omitTermFreqAndPositions,
|
float boost, boolean omitNorms, boolean omitTermFreqAndPositions,
|
||||||
String nullValue, NamedAnalyzer indexAnalyzer, NamedAnalyzer searchAnalyzer, int positionOffsetGap) {
|
String nullValue, NamedAnalyzer indexAnalyzer, NamedAnalyzer searchAnalyzer, NamedAnalyzer searchQuotedAnalyzer, int positionOffsetGap) {
|
||||||
super(names, index, store, termVector, boost, omitNorms, omitTermFreqAndPositions, indexAnalyzer, searchAnalyzer);
|
super(names, index, store, termVector, boost, omitNorms, omitTermFreqAndPositions, indexAnalyzer, searchAnalyzer);
|
||||||
this.nullValue = nullValue;
|
this.nullValue = nullValue;
|
||||||
this.positionOffsetGap = positionOffsetGap;
|
this.positionOffsetGap = positionOffsetGap;
|
||||||
|
this.searchQuotedAnalyzer = searchQuotedAnalyzer != null ? searchQuotedAnalyzer : searchAnalyzer;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -179,6 +209,11 @@ public class StringFieldMapper extends AbstractFieldMapper<String> implements Al
|
|||||||
return this.positionOffsetGap;
|
return this.positionOffsetGap;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Analyzer searchQuoteAnalyzer() {
|
||||||
|
return this.searchQuotedAnalyzer;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected Field parseCreateField(ParseContext context) throws IOException {
|
protected Field parseCreateField(ParseContext context) throws IOException {
|
||||||
String value = nullValue;
|
String value = nullValue;
|
||||||
@ -266,5 +301,8 @@ public class StringFieldMapper extends AbstractFieldMapper<String> implements Al
|
|||||||
if (positionOffsetGap != Defaults.POSITION_OFFSET_GAP) {
|
if (positionOffsetGap != Defaults.POSITION_OFFSET_GAP) {
|
||||||
builder.field("position_offset_gap", positionOffsetGap);
|
builder.field("position_offset_gap", positionOffsetGap);
|
||||||
}
|
}
|
||||||
|
if (searchQuotedAnalyzer != null && searchAnalyzer != searchQuotedAnalyzer) {
|
||||||
|
builder.field("search_quote_analyzer", searchQuotedAnalyzer.name());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -99,6 +99,12 @@ public class FieldQueryParser implements QueryParser {
|
|||||||
throw new QueryParsingException(parseContext.index(), "[query_string] analyzer [" + parser.text() + "] not found");
|
throw new QueryParsingException(parseContext.index(), "[query_string] analyzer [" + parser.text() + "] not found");
|
||||||
}
|
}
|
||||||
qpSettings.forcedAnalyzer(analyzer);
|
qpSettings.forcedAnalyzer(analyzer);
|
||||||
|
} else if ("quote_analyzer".equals(currentFieldName) || "quoteAnalyzer".equals(currentFieldName)) {
|
||||||
|
NamedAnalyzer analyzer = parseContext.analysisService().analyzer(parser.text());
|
||||||
|
if (analyzer == null) {
|
||||||
|
throw new QueryParsingException(parseContext.index(), "[query_string] analyzer [" + parser.text() + "] not found");
|
||||||
|
}
|
||||||
|
qpSettings.forcedQuoteAnalyzer(analyzer);
|
||||||
} else if ("default_operator".equals(currentFieldName) || "defaultOperator".equals(currentFieldName)) {
|
} else if ("default_operator".equals(currentFieldName) || "defaultOperator".equals(currentFieldName)) {
|
||||||
String op = parser.text();
|
String op = parser.text();
|
||||||
if ("or".equalsIgnoreCase(op)) {
|
if ("or".equalsIgnoreCase(op)) {
|
||||||
@ -120,6 +126,8 @@ public class FieldQueryParser implements QueryParser {
|
|||||||
qpSettings.rewriteMethod(QueryParsers.parseRewriteMethod(parser.textOrNull()));
|
qpSettings.rewriteMethod(QueryParsers.parseRewriteMethod(parser.textOrNull()));
|
||||||
} else if ("minimum_should_match".equals(currentFieldName) || "minimumShouldMatch".equals(currentFieldName)) {
|
} else if ("minimum_should_match".equals(currentFieldName) || "minimumShouldMatch".equals(currentFieldName)) {
|
||||||
qpSettings.minimumShouldMatch(parser.textOrNull());
|
qpSettings.minimumShouldMatch(parser.textOrNull());
|
||||||
|
} else if ("quote_field_suffix".equals(currentFieldName) || "quoteFieldSuffix".equals(currentFieldName)) {
|
||||||
|
qpSettings.quoteFieldSuffix(parser.textOrNull());
|
||||||
} else {
|
} else {
|
||||||
throw new QueryParsingException(parseContext.index(), "[field] query does not support [" + currentFieldName + "]");
|
throw new QueryParsingException(parseContext.index(), "[field] query does not support [" + currentFieldName + "]");
|
||||||
}
|
}
|
||||||
@ -133,6 +141,7 @@ public class FieldQueryParser implements QueryParser {
|
|||||||
}
|
}
|
||||||
|
|
||||||
qpSettings.defaultAnalyzer(parseContext.mapperService().searchAnalyzer());
|
qpSettings.defaultAnalyzer(parseContext.mapperService().searchAnalyzer());
|
||||||
|
qpSettings.defaultQuoteAnalyzer(parseContext.mapperService().searchQuoteAnalyzer());
|
||||||
|
|
||||||
if (qpSettings.queryString() == null) {
|
if (qpSettings.queryString() == null) {
|
||||||
throw new QueryParsingException(parseContext.index(), "No value specified for term query");
|
throw new QueryParsingException(parseContext.index(), "No value specified for term query");
|
||||||
|
@ -34,7 +34,7 @@ import static com.google.common.collect.Lists.newArrayList;
|
|||||||
* will use the {@link #defaultField(String)} set. The second, when one or more fields are added
|
* will use the {@link #defaultField(String)} set. The second, when one or more fields are added
|
||||||
* (using {@link #field(String)}), will run the parsed query against the provided fields, and combine
|
* (using {@link #field(String)}), will run the parsed query against the provided fields, and combine
|
||||||
* them either using DisMax or a plain boolean query (see {@link #useDisMax(boolean)}).
|
* them either using DisMax or a plain boolean query (see {@link #useDisMax(boolean)}).
|
||||||
*
|
* <p/>
|
||||||
* (shay.baon)
|
* (shay.baon)
|
||||||
*/
|
*/
|
||||||
public class QueryStringQueryBuilder extends BaseQueryBuilder {
|
public class QueryStringQueryBuilder extends BaseQueryBuilder {
|
||||||
@ -51,6 +51,9 @@ public class QueryStringQueryBuilder extends BaseQueryBuilder {
|
|||||||
private Operator defaultOperator;
|
private Operator defaultOperator;
|
||||||
|
|
||||||
private String analyzer;
|
private String analyzer;
|
||||||
|
private String quoteAnalyzer;
|
||||||
|
|
||||||
|
private String quoteFieldSuffix;
|
||||||
|
|
||||||
private Boolean autoGeneratePhraseQueries;
|
private Boolean autoGeneratePhraseQueries;
|
||||||
|
|
||||||
@ -163,6 +166,16 @@ public class QueryStringQueryBuilder extends BaseQueryBuilder {
|
|||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The optional analyzer used to analyze the query string for phrase searches. Note, if a field has search (quote) analyzer
|
||||||
|
* defined for it, then it will be used automatically. Defaults to the smart search analyzer.
|
||||||
|
*/
|
||||||
|
public QueryStringQueryBuilder quoteAnalyzer(String analyzer) {
|
||||||
|
this.quoteAnalyzer = analyzer;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set to true if phrase queries will be automatically generated
|
* Set to true if phrase queries will be automatically generated
|
||||||
* when the analyzer returns more than one term from whitespace
|
* when the analyzer returns more than one term from whitespace
|
||||||
@ -258,6 +271,14 @@ public class QueryStringQueryBuilder extends BaseQueryBuilder {
|
|||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* An optional field name suffix to automatically try and add to the field searched when using quoted text.
|
||||||
|
*/
|
||||||
|
public QueryStringQueryBuilder quoteFieldSuffix(String quoteFieldSuffix) {
|
||||||
|
this.quoteFieldSuffix = quoteFieldSuffix;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void doXContent(XContentBuilder builder, Params params) throws IOException {
|
protected void doXContent(XContentBuilder builder, Params params) throws IOException {
|
||||||
builder.startObject(QueryStringQueryParser.NAME);
|
builder.startObject(QueryStringQueryParser.NAME);
|
||||||
@ -291,6 +312,9 @@ public class QueryStringQueryBuilder extends BaseQueryBuilder {
|
|||||||
if (analyzer != null) {
|
if (analyzer != null) {
|
||||||
builder.field("analyzer", analyzer);
|
builder.field("analyzer", analyzer);
|
||||||
}
|
}
|
||||||
|
if (quoteAnalyzer != null) {
|
||||||
|
builder.field("quote_analyzer", quoteAnalyzer);
|
||||||
|
}
|
||||||
if (autoGeneratePhraseQueries != null) {
|
if (autoGeneratePhraseQueries != null) {
|
||||||
builder.field("auto_generate_phrase_queries", autoGeneratePhraseQueries);
|
builder.field("auto_generate_phrase_queries", autoGeneratePhraseQueries);
|
||||||
}
|
}
|
||||||
@ -324,6 +348,9 @@ public class QueryStringQueryBuilder extends BaseQueryBuilder {
|
|||||||
if (minimumShouldMatch != null) {
|
if (minimumShouldMatch != null) {
|
||||||
builder.field("minimum_should_match", minimumShouldMatch);
|
builder.field("minimum_should_match", minimumShouldMatch);
|
||||||
}
|
}
|
||||||
|
if (quoteFieldSuffix != null) {
|
||||||
|
builder.field("quote_field_suffix", quoteFieldSuffix);
|
||||||
|
}
|
||||||
builder.endObject();
|
builder.endObject();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -142,6 +142,12 @@ public class QueryStringQueryParser implements QueryParser {
|
|||||||
throw new QueryParsingException(parseContext.index(), "[query_string] analyzer [" + parser.text() + "] not found");
|
throw new QueryParsingException(parseContext.index(), "[query_string] analyzer [" + parser.text() + "] not found");
|
||||||
}
|
}
|
||||||
qpSettings.forcedAnalyzer(analyzer);
|
qpSettings.forcedAnalyzer(analyzer);
|
||||||
|
} else if ("quote_analyzer".equals(currentFieldName) || "quoteAnalyzer".equals(currentFieldName)) {
|
||||||
|
NamedAnalyzer analyzer = parseContext.analysisService().analyzer(parser.text());
|
||||||
|
if (analyzer == null) {
|
||||||
|
throw new QueryParsingException(parseContext.index(), "[query_string] quote_analyzer [" + parser.text() + "] not found");
|
||||||
|
}
|
||||||
|
qpSettings.forcedQuoteAnalyzer(analyzer);
|
||||||
} else if ("allow_leading_wildcard".equals(currentFieldName) || "allowLeadingWildcard".equals(currentFieldName)) {
|
} else if ("allow_leading_wildcard".equals(currentFieldName) || "allowLeadingWildcard".equals(currentFieldName)) {
|
||||||
qpSettings.allowLeadingWildcard(parser.booleanValue());
|
qpSettings.allowLeadingWildcard(parser.booleanValue());
|
||||||
} else if ("auto_generate_phrase_queries".equals(currentFieldName) || "autoGeneratePhraseQueries".equals(currentFieldName)) {
|
} else if ("auto_generate_phrase_queries".equals(currentFieldName) || "autoGeneratePhraseQueries".equals(currentFieldName)) {
|
||||||
@ -170,6 +176,8 @@ public class QueryStringQueryParser implements QueryParser {
|
|||||||
qpSettings.rewriteMethod(QueryParsers.parseRewriteMethod(parser.textOrNull()));
|
qpSettings.rewriteMethod(QueryParsers.parseRewriteMethod(parser.textOrNull()));
|
||||||
} else if ("minimum_should_match".equals(currentFieldName) || "minimumShouldMatch".equals(currentFieldName)) {
|
} else if ("minimum_should_match".equals(currentFieldName) || "minimumShouldMatch".equals(currentFieldName)) {
|
||||||
qpSettings.minimumShouldMatch(parser.textOrNull());
|
qpSettings.minimumShouldMatch(parser.textOrNull());
|
||||||
|
} else if ("quote_field_suffix".equals(currentFieldName) || "quoteFieldSuffix".equals(currentFieldName)) {
|
||||||
|
qpSettings.quoteFieldSuffix(parser.textOrNull());
|
||||||
} else {
|
} else {
|
||||||
throw new QueryParsingException(parseContext.index(), "[query_string] query does not support [" + currentFieldName + "]");
|
throw new QueryParsingException(parseContext.index(), "[query_string] query does not support [" + currentFieldName + "]");
|
||||||
}
|
}
|
||||||
@ -179,6 +187,7 @@ public class QueryStringQueryParser implements QueryParser {
|
|||||||
throw new QueryParsingException(parseContext.index(), "query_string must be provided with a [query]");
|
throw new QueryParsingException(parseContext.index(), "query_string must be provided with a [query]");
|
||||||
}
|
}
|
||||||
qpSettings.defaultAnalyzer(parseContext.mapperService().searchAnalyzer());
|
qpSettings.defaultAnalyzer(parseContext.mapperService().searchAnalyzer());
|
||||||
|
qpSettings.defaultQuoteAnalyzer(parseContext.mapperService().searchQuoteAnalyzer());
|
||||||
|
|
||||||
if (qpSettings.escape()) {
|
if (qpSettings.escape()) {
|
||||||
qpSettings.queryString(org.apache.lucene.queryParser.QueryParser.escape(qpSettings.queryString()));
|
qpSettings.queryString(org.apache.lucene.queryParser.QueryParser.escape(qpSettings.queryString()));
|
||||||
|
Loading…
x
Reference in New Issue
Block a user