Skip to content

Commit 3d1f71e

Browse files
committed
MappedFieldType should not extend FieldType (elastic#57666)
MappedFieldType is a combination of two concerns: * an extension of lucene's FieldType, defining how a field should be indexed * a set of query factory methods, defining how a field should be searched We want to break these two concerns apart. This commit is a first step to doing this, breaking the inheritance relationship between MappedFieldType and FieldType. MappedFieldType instead has a series of boolean flags defining whether or not the field is searchable or aggregatable, and FieldMapper has a separate FieldType passed to its constructor defining how indexing should be done. Relates to elastic#56814
1 parent 3635bd7 commit 3d1f71e

File tree

259 files changed

+3448
-4127
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

259 files changed

+3448
-4127
lines changed

modules/aggs-matrix-stats/src/test/java/org/elasticsearch/search/aggregations/matrix/stats/MatrixStatsAggregatorTests.java

+6-13
Original file line numberDiff line numberDiff line change
@@ -42,8 +42,7 @@ public class MatrixStatsAggregatorTests extends AggregatorTestCase {
4242

4343
public void testNoData() throws Exception {
4444
MappedFieldType ft =
45-
new NumberFieldMapper.NumberFieldType(NumberFieldMapper.NumberType.DOUBLE);
46-
ft.setName("field");
45+
new NumberFieldMapper.NumberFieldType("field", NumberFieldMapper.NumberType.DOUBLE);
4746

4847
try (Directory directory = newDirectory();
4948
RandomIndexWriter indexWriter = new RandomIndexWriter(random(), directory)) {
@@ -62,9 +61,7 @@ public void testNoData() throws Exception {
6261
}
6362

6463
public void testUnmapped() throws Exception {
65-
MappedFieldType ft =
66-
new NumberFieldMapper.NumberFieldType(NumberFieldMapper.NumberType.DOUBLE);
67-
ft.setName("field");
64+
MappedFieldType ft = new NumberFieldMapper.NumberFieldType("field", NumberFieldMapper.NumberType.DOUBLE);
6865

6966
try (Directory directory = newDirectory();
7067
RandomIndexWriter indexWriter = new RandomIndexWriter(random(), directory)) {
@@ -84,11 +81,9 @@ public void testUnmapped() throws Exception {
8481

8582
public void testTwoFields() throws Exception {
8683
String fieldA = "a";
87-
MappedFieldType ftA = new NumberFieldMapper.NumberFieldType(NumberFieldMapper.NumberType.DOUBLE);
88-
ftA.setName(fieldA);
84+
MappedFieldType ftA = new NumberFieldMapper.NumberFieldType(fieldA, NumberFieldMapper.NumberType.DOUBLE);
8985
String fieldB = "b";
90-
MappedFieldType ftB = new NumberFieldMapper.NumberFieldType(NumberFieldMapper.NumberType.DOUBLE);
91-
ftB.setName(fieldB);
86+
MappedFieldType ftB = new NumberFieldMapper.NumberFieldType(fieldB, NumberFieldMapper.NumberType.DOUBLE);
9287

9388
try (Directory directory = newDirectory();
9489
RandomIndexWriter indexWriter = new RandomIndexWriter(random(), directory)) {
@@ -123,11 +118,9 @@ public void testTwoFields() throws Exception {
123118

124119
public void testTwoFieldsReduce() throws Exception {
125120
String fieldA = "a";
126-
MappedFieldType ftA = new NumberFieldMapper.NumberFieldType(NumberFieldMapper.NumberType.DOUBLE);
127-
ftA.setName(fieldA);
121+
MappedFieldType ftA = new NumberFieldMapper.NumberFieldType(fieldA, NumberFieldMapper.NumberType.DOUBLE);
128122
String fieldB = "b";
129-
MappedFieldType ftB = new NumberFieldMapper.NumberFieldType(NumberFieldMapper.NumberType.DOUBLE);
130-
ftB.setName(fieldB);
123+
MappedFieldType ftB = new NumberFieldMapper.NumberFieldType(fieldB, NumberFieldMapper.NumberType.DOUBLE);
131124

132125
try (Directory directory = newDirectory();
133126
RandomIndexWriter indexWriter = new RandomIndexWriter(random(), directory)) {

modules/lang-expression/src/test/java/org/elasticsearch/script/expression/ExpressionFieldScriptTests.java

+1-1
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ public class ExpressionFieldScriptTests extends ESTestCase {
4747
public void setUp() throws Exception {
4848
super.setUp();
4949

50-
NumberFieldMapper.NumberFieldType fieldType = new NumberFieldMapper.NumberFieldType(NumberFieldMapper.NumberType.DOUBLE);
50+
NumberFieldMapper.NumberFieldType fieldType = new NumberFieldMapper.NumberFieldType("field", NumberFieldMapper.NumberType.DOUBLE);
5151
MapperService mapperService = mock(MapperService.class);
5252
when(mapperService.fieldType("field")).thenReturn(fieldType);
5353
when(mapperService.fieldType("alias")).thenReturn(fieldType);

modules/lang-expression/src/test/java/org/elasticsearch/script/expression/ExpressionNumberSortScriptTests.java

+1-1
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ public class ExpressionNumberSortScriptTests extends ESTestCase {
4646
public void setUp() throws Exception {
4747
super.setUp();
4848

49-
NumberFieldType fieldType = new NumberFieldType(NumberType.DOUBLE);
49+
NumberFieldType fieldType = new NumberFieldType("field", NumberType.DOUBLE);
5050
MapperService mapperService = mock(MapperService.class);
5151
when(mapperService.fieldType("field")).thenReturn(fieldType);
5252
when(mapperService.fieldType("alias")).thenReturn(fieldType);

modules/lang-expression/src/test/java/org/elasticsearch/script/expression/ExpressionTermsSetQueryTests.java

+1-1
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ public class ExpressionTermsSetQueryTests extends ESTestCase {
4646
public void setUp() throws Exception {
4747
super.setUp();
4848

49-
NumberFieldType fieldType = new NumberFieldType(NumberType.DOUBLE);
49+
NumberFieldType fieldType = new NumberFieldType("field", NumberType.DOUBLE);
5050
MapperService mapperService = mock(MapperService.class);
5151
when(mapperService.fieldType("field")).thenReturn(fieldType);
5252
when(mapperService.fieldType("alias")).thenReturn(fieldType);

modules/mapper-extras/src/main/java/org/elasticsearch/index/mapper/RankFeatureFieldMapper.java

+28-45
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
package org.elasticsearch.index.mapper;
2121

2222
import org.apache.lucene.document.FeatureField;
23+
import org.apache.lucene.document.FieldType;
2324
import org.apache.lucene.index.IndexOptions;
2425
import org.apache.lucene.index.Term;
2526
import org.apache.lucene.search.Query;
@@ -36,7 +37,6 @@
3637
import java.util.Iterator;
3738
import java.util.List;
3839
import java.util.Map;
39-
import java.util.Objects;
4040

4141
/**
4242
* A {@link FieldMapper} that exposes Lucene's {@link FeatureField}.
@@ -46,40 +46,34 @@ public class RankFeatureFieldMapper extends FieldMapper {
4646
public static final String CONTENT_TYPE = "rank_feature";
4747

4848
public static class Defaults {
49-
public static final MappedFieldType FIELD_TYPE = new RankFeatureFieldType();
49+
public static final FieldType FIELD_TYPE = new FieldType();
5050

5151
static {
5252
FIELD_TYPE.setTokenized(false);
5353
FIELD_TYPE.setIndexOptions(IndexOptions.NONE);
54-
FIELD_TYPE.setHasDocValues(false);
5554
FIELD_TYPE.setOmitNorms(true);
5655
FIELD_TYPE.freeze();
5756
}
5857
}
5958

6059
public static class Builder extends FieldMapper.Builder<Builder> {
6160

61+
private boolean positiveScoreImpact = true;
62+
6263
public Builder(String name) {
63-
super(name, Defaults.FIELD_TYPE, Defaults.FIELD_TYPE);
64+
super(name, Defaults.FIELD_TYPE);
6465
builder = this;
6566
}
6667

67-
@Override
68-
public RankFeatureFieldType fieldType() {
69-
return (RankFeatureFieldType) super.fieldType();
70-
}
71-
7268
public Builder positiveScoreImpact(boolean v) {
73-
fieldType().setPositiveScoreImpact(v);
69+
this.positiveScoreImpact = v;
7470
return builder;
7571
}
7672

7773
@Override
7874
public RankFeatureFieldMapper build(BuilderContext context) {
79-
setupFieldType(context);
80-
return new RankFeatureFieldMapper(
81-
name, fieldType, defaultFieldType,
82-
context.indexSettings(), multiFieldsBuilder.build(this, context), copyTo);
75+
return new RankFeatureFieldMapper(name, fieldType, new RankFeatureFieldType(buildFullName(context), meta, positiveScoreImpact),
76+
context.indexSettings(), multiFieldsBuilder.build(this, context), copyTo, positiveScoreImpact);
8377
}
8478
}
8579

@@ -102,9 +96,11 @@ public Mapper.Builder<?> parse(String name, Map<String, Object> node, ParserCont
10296

10397
public static final class RankFeatureFieldType extends MappedFieldType {
10498

105-
private boolean positiveScoreImpact = true;
99+
private final boolean positiveScoreImpact;
106100

107-
public RankFeatureFieldType() {
101+
public RankFeatureFieldType(String name, Map<String, String> meta, boolean positiveScoreImpact) {
102+
super(name, true, false, meta);
103+
this.positiveScoreImpact = positiveScoreImpact;
108104
setIndexAnalyzer(Lucene.KEYWORD_ANALYZER);
109105
setSearchAnalyzer(Lucene.KEYWORD_ANALYZER);
110106
}
@@ -118,22 +114,6 @@ public RankFeatureFieldType clone() {
118114
return new RankFeatureFieldType(this);
119115
}
120116

121-
@Override
122-
public boolean equals(Object o) {
123-
if (super.equals(o) == false) {
124-
return false;
125-
}
126-
RankFeatureFieldType other = (RankFeatureFieldType) o;
127-
return Objects.equals(positiveScoreImpact, other.positiveScoreImpact);
128-
}
129-
130-
@Override
131-
public int hashCode() {
132-
int h = super.hashCode();
133-
h = 31 * h + Objects.hashCode(positiveScoreImpact);
134-
return h;
135-
}
136-
137117
@Override
138118
public String typeName() {
139119
return CONTENT_TYPE;
@@ -143,11 +123,6 @@ public boolean positiveScoreImpact() {
143123
return positiveScoreImpact;
144124
}
145125

146-
public void setPositiveScoreImpact(boolean positiveScoreImpact) {
147-
checkIfFrozen();
148-
this.positiveScoreImpact = positiveScoreImpact;
149-
}
150-
151126
@Override
152127
public Query existsQuery(QueryShardContext context) {
153128
return new TermQuery(new Term("_feature", name()));
@@ -164,10 +139,14 @@ public Query termQuery(Object value, QueryShardContext context) {
164139
}
165140
}
166141

167-
private RankFeatureFieldMapper(String simpleName, MappedFieldType fieldType, MappedFieldType defaultFieldType,
168-
Settings indexSettings, MultiFields multiFields, CopyTo copyTo) {
169-
super(simpleName, fieldType, defaultFieldType, indexSettings, multiFields, copyTo);
142+
private final boolean positiveScoreImpact;
143+
144+
private RankFeatureFieldMapper(String simpleName, FieldType fieldType, MappedFieldType mappedFieldType,
145+
Settings indexSettings, MultiFields multiFields, CopyTo copyTo,
146+
boolean positiveScoreImpact) {
147+
super(simpleName, fieldType, mappedFieldType, indexSettings, multiFields, copyTo);
170148
assert fieldType.indexOptions().compareTo(IndexOptions.DOCS_AND_FREQS) <= 0;
149+
this.positiveScoreImpact = positiveScoreImpact;
171150
}
172151

173152
@Override
@@ -202,7 +181,7 @@ protected void parseCreateField(ParseContext context) throws IOException {
202181
name() + "] in the same document");
203182
}
204183

205-
if (fieldType().positiveScoreImpact() == false) {
184+
if (positiveScoreImpact == false) {
206185
value = 1 / value;
207186
}
208187

@@ -218,15 +197,19 @@ protected String contentType() {
218197
protected void doXContentBody(XContentBuilder builder, boolean includeDefaults, Params params) throws IOException {
219198
super.doXContentBody(builder, includeDefaults, params);
220199

221-
if (includeDefaults || fieldType().positiveScoreImpact() == false) {
222-
builder.field("positive_score_impact", fieldType().positiveScoreImpact());
200+
if (includeDefaults || positiveScoreImpact == false) {
201+
builder.field("positive_score_impact", positiveScoreImpact);
223202
}
224203
}
225204

205+
@Override
206+
protected boolean docValuesByDefault() {
207+
return false;
208+
}
209+
226210
@Override
227211
protected void mergeOptions(FieldMapper other, List<String> conflicts) {
228-
RankFeatureFieldType ft = (RankFeatureFieldType) other.fieldType();
229-
if (fieldType().positiveScoreImpact != ft.positiveScoreImpact()) {
212+
if (positiveScoreImpact != ((RankFeatureFieldMapper)other).positiveScoreImpact) {
230213
conflicts.add("mapper [" + name() + "] has different [positive_score_impact] values");
231214
}
232215
}

modules/mapper-extras/src/main/java/org/elasticsearch/index/mapper/RankFeatureMetaFieldMapper.java

+13-18
Original file line numberDiff line numberDiff line change
@@ -19,9 +19,9 @@
1919

2020
package org.elasticsearch.index.mapper;
2121

22+
import org.apache.lucene.document.FieldType;
2223
import org.apache.lucene.index.IndexOptions;
2324
import org.apache.lucene.search.Query;
24-
import org.elasticsearch.common.lucene.Lucene;
2525
import org.elasticsearch.common.settings.Settings;
2626
import org.elasticsearch.common.xcontent.XContentBuilder;
2727
import org.elasticsearch.index.query.QueryShardContext;
@@ -42,45 +42,41 @@ public class RankFeatureMetaFieldMapper extends MetadataFieldMapper {
4242
public static final String CONTENT_TYPE = "_feature";
4343

4444
public static class Defaults {
45-
public static final MappedFieldType FIELD_TYPE = new RankFeatureMetaFieldType();
45+
public static final FieldType FIELD_TYPE = new FieldType();
4646

4747
static {
4848
FIELD_TYPE.setIndexOptions(IndexOptions.DOCS_AND_FREQS);
4949
FIELD_TYPE.setTokenized(true);
5050
FIELD_TYPE.setStored(false);
5151
FIELD_TYPE.setOmitNorms(true);
52-
FIELD_TYPE.setIndexAnalyzer(Lucene.KEYWORD_ANALYZER);
53-
FIELD_TYPE.setSearchAnalyzer(Lucene.KEYWORD_ANALYZER);
54-
FIELD_TYPE.setName(NAME);
5552
FIELD_TYPE.freeze();
5653
}
5754
}
5855

5956
public static class Builder extends MetadataFieldMapper.Builder<Builder> {
6057

61-
public Builder(MappedFieldType existing) {
62-
super(NAME, existing == null ? Defaults.FIELD_TYPE : existing, Defaults.FIELD_TYPE);
58+
public Builder() {
59+
super(NAME, Defaults.FIELD_TYPE);
6360
}
6461

6562
@Override
6663
public RankFeatureMetaFieldMapper build(BuilderContext context) {
67-
setupFieldType(context);
68-
return new RankFeatureMetaFieldMapper(fieldType, context.indexSettings());
64+
return new RankFeatureMetaFieldMapper(context.indexSettings());
6965
}
7066
}
7167

7268
public static class TypeParser implements MetadataFieldMapper.TypeParser {
7369
@Override
7470
public MetadataFieldMapper.Builder<?> parse(String name,
7571
Map<String, Object> node, ParserContext parserContext) throws MapperParsingException {
76-
return new Builder(parserContext.mapperService().fieldType(NAME));
72+
return new Builder();
7773
}
7874

7975
@Override
8076
public MetadataFieldMapper getDefault(MappedFieldType fieldType, ParserContext context) {
8177
final Settings indexSettings = context.mapperService().getIndexSettings().getSettings();
8278
if (fieldType != null) {
83-
return new RankFeatureMetaFieldMapper(indexSettings, fieldType);
79+
return new RankFeatureMetaFieldMapper(indexSettings);
8480
} else {
8581
return parse(NAME, Collections.emptyMap(), context)
8682
.build(new BuilderContext(indexSettings, new ContentPath(1)));
@@ -90,7 +86,10 @@ public MetadataFieldMapper getDefault(MappedFieldType fieldType, ParserContext c
9086

9187
public static final class RankFeatureMetaFieldType extends MappedFieldType {
9288

93-
public RankFeatureMetaFieldType() {
89+
public static final RankFeatureMetaFieldType INSTANCE = new RankFeatureMetaFieldType();
90+
91+
private RankFeatureMetaFieldType() {
92+
super(NAME, false, false, Collections.emptyMap());
9493
}
9594

9695
protected RankFeatureMetaFieldType(RankFeatureMetaFieldType ref) {
@@ -118,12 +117,8 @@ public Query termQuery(Object value, QueryShardContext context) {
118117
}
119118
}
120119

121-
private RankFeatureMetaFieldMapper(Settings indexSettings, MappedFieldType existing) {
122-
this(existing.clone(), indexSettings);
123-
}
124-
125-
private RankFeatureMetaFieldMapper(MappedFieldType fieldType, Settings indexSettings) {
126-
super(NAME, fieldType, Defaults.FIELD_TYPE, indexSettings);
120+
private RankFeatureMetaFieldMapper(Settings indexSettings) {
121+
super(Defaults.FIELD_TYPE, RankFeatureMetaFieldType.INSTANCE, indexSettings);
127122
}
128123

129124
@Override

0 commit comments

Comments
 (0)