mirror of
https://github.com/honeymoose/OpenSearch.git
synced 2025-02-18 10:54:54 +00:00
Rename index_prefix to index_prefixes (#30932)
This commit also adds index_prefixes tests to TextFieldMapperTests to ensure that cloning and wire-serialization work correctly
This commit is contained in:
parent
a0af0e7f1e
commit
67905c85a5
@ -89,7 +89,7 @@ The following parameters are accepted by `text` fields:
|
|||||||
What information should be stored in the index, for search and highlighting purposes.
|
What information should be stored in the index, for search and highlighting purposes.
|
||||||
Defaults to `positions`.
|
Defaults to `positions`.
|
||||||
|
|
||||||
<<index-prefix-config,`index_prefix`>>::
|
<<index-prefix-config,`index_prefixes`>>::
|
||||||
|
|
||||||
If enabled, term prefixes of between 2 and 5 characters are indexed into a
|
If enabled, term prefixes of between 2 and 5 characters are indexed into a
|
||||||
separate field. This allows prefix searches to run more efficiently, at
|
separate field. This allows prefix searches to run more efficiently, at
|
||||||
@ -138,7 +138,7 @@ The following parameters are accepted by `text` fields:
|
|||||||
[[index-prefix-config]]
|
[[index-prefix-config]]
|
||||||
==== Index Prefix configuration
|
==== Index Prefix configuration
|
||||||
|
|
||||||
Text fields may also index term prefixes to speed up prefix searches. The `index_prefix`
|
Text fields may also index term prefixes to speed up prefix searches. The `index_prefixes`
|
||||||
parameter is configured as below. Either or both of `min_chars` and `max_chars` may be excluded.
|
parameter is configured as below. Either or both of `min_chars` and `max_chars` may be excluded.
|
||||||
Both values are treated as inclusive
|
Both values are treated as inclusive
|
||||||
|
|
||||||
@ -151,7 +151,7 @@ PUT my_index
|
|||||||
"properties": {
|
"properties": {
|
||||||
"full_name": {
|
"full_name": {
|
||||||
"type": "text",
|
"type": "text",
|
||||||
"index_prefix" : {
|
"index_prefixes" : {
|
||||||
"min_chars" : 1, <1>
|
"min_chars" : 1, <1>
|
||||||
"max_chars" : 10 <2>
|
"max_chars" : 10 <2>
|
||||||
}
|
}
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
"search with index prefixes":
|
"search with index prefixes":
|
||||||
- skip:
|
- skip:
|
||||||
version: " - 6.99.99"
|
version: " - 6.99.99"
|
||||||
reason: index_prefix is only available as of 6.3.0
|
reason: index_prefixes is only available as of 6.3.0
|
||||||
- do:
|
- do:
|
||||||
indices.create:
|
indices.create:
|
||||||
index: test
|
index: test
|
||||||
@ -12,7 +12,7 @@
|
|||||||
properties:
|
properties:
|
||||||
text:
|
text:
|
||||||
type: text
|
type: text
|
||||||
index_prefix:
|
index_prefixes:
|
||||||
min_chars: 1
|
min_chars: 1
|
||||||
max_chars: 10
|
max_chars: 10
|
||||||
|
|
||||||
|
@ -156,7 +156,7 @@ public class TextFieldMapper extends FieldMapper {
|
|||||||
PrefixFieldMapper prefixMapper = null;
|
PrefixFieldMapper prefixMapper = null;
|
||||||
if (prefixFieldType != null) {
|
if (prefixFieldType != null) {
|
||||||
if (fieldType().isSearchable() == false) {
|
if (fieldType().isSearchable() == false) {
|
||||||
throw new IllegalArgumentException("Cannot set index_prefix on unindexed field [" + name() + "]");
|
throw new IllegalArgumentException("Cannot set index_prefixes on unindexed field [" + name() + "]");
|
||||||
}
|
}
|
||||||
if (fieldType.indexOptions() == IndexOptions.DOCS_AND_FREQS_AND_POSITIONS_AND_OFFSETS) {
|
if (fieldType.indexOptions() == IndexOptions.DOCS_AND_FREQS_AND_POSITIONS_AND_OFFSETS) {
|
||||||
prefixFieldType.setIndexOptions(IndexOptions.DOCS_AND_FREQS_AND_POSITIONS_AND_OFFSETS);
|
prefixFieldType.setIndexOptions(IndexOptions.DOCS_AND_FREQS_AND_POSITIONS_AND_OFFSETS);
|
||||||
@ -203,7 +203,7 @@ public class TextFieldMapper extends FieldMapper {
|
|||||||
builder.fielddataFrequencyFilter(minFrequency, maxFrequency, minSegmentSize);
|
builder.fielddataFrequencyFilter(minFrequency, maxFrequency, minSegmentSize);
|
||||||
DocumentMapperParser.checkNoRemainingFields(propName, frequencyFilter, parserContext.indexVersionCreated());
|
DocumentMapperParser.checkNoRemainingFields(propName, frequencyFilter, parserContext.indexVersionCreated());
|
||||||
iterator.remove();
|
iterator.remove();
|
||||||
} else if (propName.equals("index_prefix")) {
|
} else if (propName.equals("index_prefixes")) {
|
||||||
Map<?, ?> indexPrefix = (Map<?, ?>) propNode;
|
Map<?, ?> indexPrefix = (Map<?, ?>) propNode;
|
||||||
int minChars = XContentMapValues.nodeIntegerValue(indexPrefix.remove("min_chars"),
|
int minChars = XContentMapValues.nodeIntegerValue(indexPrefix.remove("min_chars"),
|
||||||
Defaults.INDEX_PREFIX_MIN_CHARS);
|
Defaults.INDEX_PREFIX_MIN_CHARS);
|
||||||
@ -243,7 +243,7 @@ public class TextFieldMapper extends FieldMapper {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static final class PrefixFieldType extends StringFieldType {
|
static final class PrefixFieldType extends StringFieldType {
|
||||||
|
|
||||||
final int minChars;
|
final int minChars;
|
||||||
final int maxChars;
|
final int maxChars;
|
||||||
@ -268,14 +268,14 @@ public class TextFieldMapper extends FieldMapper {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void doXContent(XContentBuilder builder) throws IOException {
|
void doXContent(XContentBuilder builder) throws IOException {
|
||||||
builder.startObject("index_prefix");
|
builder.startObject("index_prefixes");
|
||||||
builder.field("min_chars", minChars);
|
builder.field("min_chars", minChars);
|
||||||
builder.field("max_chars", maxChars);
|
builder.field("max_chars", maxChars);
|
||||||
builder.endObject();
|
builder.endObject();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public MappedFieldType clone() {
|
public PrefixFieldType clone() {
|
||||||
return new PrefixFieldType(name(), minChars, maxChars);
|
return new PrefixFieldType(name(), minChars, maxChars);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -305,6 +305,22 @@ public class TextFieldMapper extends FieldMapper {
|
|||||||
public Query existsQuery(QueryShardContext context) {
|
public Query existsQuery(QueryShardContext context) {
|
||||||
throw new UnsupportedOperationException();
|
throw new UnsupportedOperationException();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object o) {
|
||||||
|
if (this == o) return true;
|
||||||
|
if (o == null || getClass() != o.getClass()) return false;
|
||||||
|
if (!super.equals(o)) return false;
|
||||||
|
PrefixFieldType that = (PrefixFieldType) o;
|
||||||
|
return minChars == that.minChars &&
|
||||||
|
maxChars == that.maxChars;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
|
||||||
|
return Objects.hash(super.hashCode(), minChars, maxChars);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static final class PrefixFieldMapper extends FieldMapper {
|
private static final class PrefixFieldMapper extends FieldMapper {
|
||||||
@ -355,6 +371,9 @@ public class TextFieldMapper extends FieldMapper {
|
|||||||
this.fielddataMinFrequency = ref.fielddataMinFrequency;
|
this.fielddataMinFrequency = ref.fielddataMinFrequency;
|
||||||
this.fielddataMaxFrequency = ref.fielddataMaxFrequency;
|
this.fielddataMaxFrequency = ref.fielddataMaxFrequency;
|
||||||
this.fielddataMinSegmentSize = ref.fielddataMinSegmentSize;
|
this.fielddataMinSegmentSize = ref.fielddataMinSegmentSize;
|
||||||
|
if (ref.prefixFieldType != null) {
|
||||||
|
this.prefixFieldType = ref.prefixFieldType.clone();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public TextFieldType clone() {
|
public TextFieldType clone() {
|
||||||
@ -368,6 +387,7 @@ public class TextFieldMapper extends FieldMapper {
|
|||||||
}
|
}
|
||||||
TextFieldType that = (TextFieldType) o;
|
TextFieldType that = (TextFieldType) o;
|
||||||
return fielddata == that.fielddata
|
return fielddata == that.fielddata
|
||||||
|
&& Objects.equals(prefixFieldType, that.prefixFieldType)
|
||||||
&& fielddataMinFrequency == that.fielddataMinFrequency
|
&& fielddataMinFrequency == that.fielddataMinFrequency
|
||||||
&& fielddataMaxFrequency == that.fielddataMaxFrequency
|
&& fielddataMaxFrequency == that.fielddataMaxFrequency
|
||||||
&& fielddataMinSegmentSize == that.fielddataMinSegmentSize;
|
&& fielddataMinSegmentSize == that.fielddataMinSegmentSize;
|
||||||
@ -375,7 +395,7 @@ public class TextFieldMapper extends FieldMapper {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int hashCode() {
|
public int hashCode() {
|
||||||
return Objects.hash(super.hashCode(), fielddata,
|
return Objects.hash(super.hashCode(), fielddata, prefixFieldType,
|
||||||
fielddataMinFrequency, fielddataMaxFrequency, fielddataMinSegmentSize);
|
fielddataMinFrequency, fielddataMaxFrequency, fielddataMinSegmentSize);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -420,6 +440,10 @@ public class TextFieldMapper extends FieldMapper {
|
|||||||
this.prefixFieldType = prefixFieldType;
|
this.prefixFieldType = prefixFieldType;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public PrefixFieldType getPrefixFieldType() {
|
||||||
|
return this.prefixFieldType;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String typeName() {
|
public String typeName() {
|
||||||
return CONTENT_TYPE;
|
return CONTENT_TYPE;
|
||||||
|
@ -607,7 +607,7 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.startObject("index_prefix").endObject()
|
.startObject("index_prefixes").endObject()
|
||||||
.field("index_options", "offsets")
|
.field("index_options", "offsets")
|
||||||
.endObject().endObject().endObject().endObject());
|
.endObject().endObject().endObject().endObject());
|
||||||
|
|
||||||
@ -623,7 +623,7 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.startObject("index_prefix").endObject()
|
.startObject("index_prefixes").endObject()
|
||||||
.field("index_options", "positions")
|
.field("index_options", "positions")
|
||||||
.endObject().endObject().endObject().endObject());
|
.endObject().endObject().endObject().endObject());
|
||||||
|
|
||||||
@ -640,7 +640,7 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.startObject("index_prefix").endObject()
|
.startObject("index_prefixes").endObject()
|
||||||
.field("term_vector", "with_positions_offsets")
|
.field("term_vector", "with_positions_offsets")
|
||||||
.endObject().endObject().endObject().endObject());
|
.endObject().endObject().endObject().endObject());
|
||||||
|
|
||||||
@ -657,7 +657,7 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.startObject("index_prefix").endObject()
|
.startObject("index_prefixes").endObject()
|
||||||
.field("term_vector", "with_positions")
|
.field("term_vector", "with_positions")
|
||||||
.endObject().endObject().endObject().endObject());
|
.endObject().endObject().endObject().endObject());
|
||||||
|
|
||||||
@ -682,7 +682,7 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.startObject("index_prefix")
|
.startObject("index_prefixes")
|
||||||
.field("min_chars", 1)
|
.field("min_chars", 1)
|
||||||
.field("max_chars", 10)
|
.field("max_chars", 10)
|
||||||
.endObject()
|
.endObject()
|
||||||
@ -716,7 +716,7 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.startObject("index_prefix").endObject()
|
.startObject("index_prefixes").endObject()
|
||||||
.endObject().endObject()
|
.endObject().endObject()
|
||||||
.endObject().endObject());
|
.endObject().endObject());
|
||||||
CompressedXContent json = new CompressedXContent(mapping);
|
CompressedXContent json = new CompressedXContent(mapping);
|
||||||
@ -741,7 +741,7 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.startObject("index_prefix")
|
.startObject("index_prefixes")
|
||||||
.field("min_chars", 1)
|
.field("min_chars", 1)
|
||||||
.field("max_chars", 10)
|
.field("max_chars", 10)
|
||||||
.endObject()
|
.endObject()
|
||||||
@ -760,7 +760,7 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.startObject("index_prefix")
|
.startObject("index_prefixes")
|
||||||
.field("min_chars", 1)
|
.field("min_chars", 1)
|
||||||
.field("max_chars", 10)
|
.field("max_chars", 10)
|
||||||
.endObject()
|
.endObject()
|
||||||
@ -783,7 +783,7 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.startObject("index_prefix")
|
.startObject("index_prefixes")
|
||||||
.field("min_chars", 11)
|
.field("min_chars", 11)
|
||||||
.field("max_chars", 10)
|
.field("max_chars", 10)
|
||||||
.endObject()
|
.endObject()
|
||||||
@ -800,7 +800,7 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.startObject("index_prefix")
|
.startObject("index_prefixes")
|
||||||
.field("min_chars", 0)
|
.field("min_chars", 0)
|
||||||
.field("max_chars", 10)
|
.field("max_chars", 10)
|
||||||
.endObject()
|
.endObject()
|
||||||
@ -817,7 +817,7 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.startObject("index_prefix")
|
.startObject("index_prefixes")
|
||||||
.field("min_chars", 1)
|
.field("min_chars", 1)
|
||||||
.field("max_chars", 25)
|
.field("max_chars", 25)
|
||||||
.endObject()
|
.endObject()
|
||||||
@ -834,13 +834,13 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("analyzer", "english")
|
.field("analyzer", "english")
|
||||||
.field("index_prefix", (String) null)
|
.field("index_prefixes", (String) null)
|
||||||
.endObject().endObject()
|
.endObject().endObject()
|
||||||
.endObject().endObject());
|
.endObject().endObject());
|
||||||
MapperParsingException e = expectThrows(MapperParsingException.class,
|
MapperParsingException e = expectThrows(MapperParsingException.class,
|
||||||
() -> parser.parse("type", new CompressedXContent(badConfigMapping))
|
() -> parser.parse("type", new CompressedXContent(badConfigMapping))
|
||||||
);
|
);
|
||||||
assertThat(e.getMessage(), containsString("[index_prefix] must not have a [null] value"));
|
assertThat(e.getMessage(), containsString("[index_prefixes] must not have a [null] value"));
|
||||||
}
|
}
|
||||||
|
|
||||||
{
|
{
|
||||||
@ -848,13 +848,13 @@ public class TextFieldMapperTests extends ESSingleNodeTestCase {
|
|||||||
.startObject("properties").startObject("field")
|
.startObject("properties").startObject("field")
|
||||||
.field("type", "text")
|
.field("type", "text")
|
||||||
.field("index", "false")
|
.field("index", "false")
|
||||||
.startObject("index_prefix").endObject()
|
.startObject("index_prefixes").endObject()
|
||||||
.endObject().endObject()
|
.endObject().endObject()
|
||||||
.endObject().endObject());
|
.endObject().endObject());
|
||||||
IllegalArgumentException e = expectThrows(IllegalArgumentException.class,
|
IllegalArgumentException e = expectThrows(IllegalArgumentException.class,
|
||||||
() -> parser.parse("type", new CompressedXContent(badConfigMapping))
|
() -> parser.parse("type", new CompressedXContent(badConfigMapping))
|
||||||
);
|
);
|
||||||
assertThat(e.getMessage(), containsString("Cannot set index_prefix on unindexed field [field]"));
|
assertThat(e.getMessage(), containsString("Cannot set index_prefixes on unindexed field [field]"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -71,6 +71,19 @@ public class TextFieldTypeTests extends FieldTypeTestCase {
|
|||||||
tft.setFielddataMinSegmentSize(1000);
|
tft.setFielddataMinSegmentSize(1000);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
addModifier(new Modifier("index_prefixes", true) {
|
||||||
|
@Override
|
||||||
|
public void modify(MappedFieldType ft) {
|
||||||
|
TextFieldMapper.TextFieldType tft = (TextFieldMapper.TextFieldType)ft;
|
||||||
|
TextFieldMapper.PrefixFieldType pft = tft.getPrefixFieldType();
|
||||||
|
if (pft == null) {
|
||||||
|
tft.setPrefixFieldType(new TextFieldMapper.PrefixFieldType(ft.name(), 3, 3));
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
tft.setPrefixFieldType(null);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testTermQuery() {
|
public void testTermQuery() {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user