Skip to content

Commit cf575f4

Browse files
authored
Make NestedObjectMapper its own class (elastic#74410)
Nested objects are implemented via a Nested class directly on object mappers, even though nested and non-nested objects have quite different semantics. In addition, most call-sites that need to get an object mapper in fact need a nested object mapper. To make it clearer that nested and object mappers are different beasts with different implementations and different requirements, we should split them into different classes.
1 parent dbfd86a commit cf575f4

40 files changed

+527
-386
lines changed

server/src/main/java/org/elasticsearch/action/fieldcaps/TransportFieldCapabilitiesAction.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -365,7 +365,7 @@ private FieldCapabilitiesIndexResponse shardOperation(final FieldCapabilitiesInd
365365
if (searchExecutionContext.getFieldType(parentField) == null) {
366366
// no field type, it must be an object field
367367
ObjectMapper mapper = searchExecutionContext.getObjectMapper(parentField);
368-
String type = mapper.nested().isNested() ? "nested" : "object";
368+
String type = mapper.isNested() ? "nested" : "object";
369369
IndexFieldCapabilities fieldCap = new IndexFieldCapabilities(parentField, type,
370370
false, false, false, Collections.emptyMap());
371371
responseMap.put(parentField, fieldCap);

server/src/main/java/org/elasticsearch/index/cache/bitset/BitsetFilterCache.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@
3838
import org.elasticsearch.index.IndexWarmer.TerminationHandle;
3939
import org.elasticsearch.index.mapper.MapperService;
4040
import org.elasticsearch.index.mapper.MappingLookup;
41-
import org.elasticsearch.index.mapper.ObjectMapper;
41+
import org.elasticsearch.index.mapper.NestedObjectMapper;
4242
import org.elasticsearch.index.shard.IndexShard;
4343
import org.elasticsearch.index.shard.ShardId;
4444
import org.elasticsearch.index.shard.ShardUtils;
@@ -232,7 +232,7 @@ public IndexWarmer.TerminationHandle warmReader(final IndexShard indexShard, fin
232232
MappingLookup lookup = mapperService.mappingLookup();
233233
if (lookup.hasNested()) {
234234
warmUp.add(Queries.newNonNestedFilter());
235-
lookup.getNestedParentMappers().stream().map(ObjectMapper::nestedTypeFilter).forEach(warmUp::add);
235+
lookup.getNestedParentMappers().stream().map(NestedObjectMapper::nestedTypeFilter).forEach(warmUp::add);
236236
}
237237

238238
final CountDownLatch latch = new CountDownLatch(reader.leaves().size() * warmUp.size());

server/src/main/java/org/elasticsearch/index/mapper/DocumentMapper.java

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@
88

99
package org.elasticsearch.index.mapper;
1010

11-
import org.elasticsearch.Version;
1211
import org.elasticsearch.common.compress.CompressedXContent;
1312
import org.elasticsearch.index.IndexSettings;
1413

@@ -24,7 +23,7 @@ public class DocumentMapper {
2423
* @return the newly created document mapper
2524
*/
2625
public static DocumentMapper createEmpty(MapperService mapperService) {
27-
RootObjectMapper root = new RootObjectMapper.Builder(MapperService.SINGLE_MAPPING_NAME, Version.CURRENT).build(new ContentPath(1));
26+
RootObjectMapper root = new RootObjectMapper.Builder(MapperService.SINGLE_MAPPING_NAME).build(new ContentPath(1));
2827
MetadataFieldMapper[] metadata = mapperService.getMetadataMappers().values().toArray(new MetadataFieldMapper[0]);
2928
Mapping mapping = new Mapping(root, metadata, null);
3029
return new DocumentMapper(mapperService.documentParser(), mapping);

server/src/main/java/org/elasticsearch/index/mapper/DocumentParser.java

Lines changed: 9 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -427,9 +427,8 @@ static void parseObjectOrNested(DocumentParserContext context, ObjectMapper mapp
427427
+ "] as object, but found a concrete value");
428428
}
429429

430-
ObjectMapper.Nested nested = mapper.nested();
431-
if (nested.isNested()) {
432-
context = nestedContext(context, mapper);
430+
if (mapper.isNested()) {
431+
context = nestedContext(context, (NestedObjectMapper) mapper);
433432
}
434433

435434
// if we are at the end of the previous object, advance
@@ -443,8 +442,8 @@ static void parseObjectOrNested(DocumentParserContext context, ObjectMapper mapp
443442

444443
innerParseObject(context, mapper, parser, currentFieldName, token);
445444
// restore the enable path flag
446-
if (nested.isNested()) {
447-
nested(context, nested);
445+
if (mapper.isNested()) {
446+
nested(context, (NestedObjectMapper) mapper);
448447
}
449448
}
450449

@@ -476,7 +475,7 @@ private static void innerParseObject(DocumentParserContext context, ObjectMapper
476475
}
477476
}
478477

479-
private static void nested(DocumentParserContext context, ObjectMapper.Nested nested) {
478+
private static void nested(DocumentParserContext context, NestedObjectMapper nested) {
480479
LuceneDocument nestedDoc = context.doc();
481480
LuceneDocument parentDoc = nestedDoc.getParent();
482481
Version indexVersion = context.indexSettings().getIndexVersionCreated();
@@ -501,7 +500,7 @@ private static void addFields(Version indexCreatedVersion, LuceneDocument nested
501500
}
502501
}
503502

504-
private static DocumentParserContext nestedContext(DocumentParserContext context, ObjectMapper mapper) {
503+
private static DocumentParserContext nestedContext(DocumentParserContext context, NestedObjectMapper mapper) {
505504
context = context.createNestedContext(mapper.fullPath());
506505
LuceneDocument nestedDoc = context.doc();
507506
LuceneDocument parentDoc = nestedDoc.getParent();
@@ -792,7 +791,7 @@ private static Tuple<Integer, ObjectMapper> getDynamicParentMapper(DocumentParse
792791
context.sourceToParse().dynamicTemplates().get(currentPath) + "]");
793792
}
794793
mapper = (ObjectMapper) fieldMapper;
795-
if (mapper.nested() != ObjectMapper.Nested.NO) {
794+
if (mapper.isNested()) {
796795
throw new MapperParsingException("It is forbidden to create dynamic nested objects (["
797796
+ currentPath + "]) through `copy_to` or dots in field names");
798797
}
@@ -854,7 +853,7 @@ private static Mapper getMapper(final DocumentParserContext context,
854853
return null;
855854
}
856855
objectMapper = (ObjectMapper)mapper;
857-
if (objectMapper.nested().isNested()) {
856+
if (objectMapper.isNested()) {
858857
throw new MapperParsingException("Cannot add a value for field ["
859858
+ fieldName + "] since one of the intermediate objects is mapped as a nested object: ["
860859
+ mapper.name() + "]");
@@ -966,7 +965,7 @@ protected String contentType() {
966965

967966
private static class NoOpObjectMapper extends ObjectMapper {
968967
NoOpObjectMapper(String name, String fullPath) {
969-
super(name, fullPath, new Explicit<>(true, false), Nested.NO, Dynamic.RUNTIME, Collections.emptyMap(), Version.CURRENT);
968+
super(name, fullPath, new Explicit<>(true, false), Dynamic.RUNTIME, Collections.emptyMap());
970969
}
971970
}
972971

server/src/main/java/org/elasticsearch/index/mapper/DynamicFieldsBuilder.java

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -125,8 +125,7 @@ void createDynamicFieldFromValue(final DocumentParserContext context,
125125
*/
126126
Mapper createDynamicObjectMapper(DocumentParserContext context, String name) {
127127
Mapper mapper = createObjectMapperFromTemplate(context, name);
128-
return mapper != null ? mapper :
129-
new ObjectMapper.Builder(name, context.indexSettings().getIndexVersionCreated()).enabled(true).build(context.path());
128+
return mapper != null ? mapper : new ObjectMapper.Builder(name).enabled(true).build(context.path());
130129
}
131130

132131
/**

server/src/main/java/org/elasticsearch/index/mapper/Mapping.java

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@
99
package org.elasticsearch.index.mapper;
1010

1111
import org.elasticsearch.ElasticsearchGenerationException;
12-
import org.elasticsearch.Version;
1312
import org.elasticsearch.common.Strings;
1413
import org.elasticsearch.common.compress.CompressedXContent;
1514
import org.elasticsearch.common.xcontent.ToXContent;
@@ -36,7 +35,7 @@
3635
public final class Mapping implements ToXContentFragment {
3736

3837
public static final Mapping EMPTY = new Mapping(
39-
new RootObjectMapper.Builder("_doc", Version.CURRENT).build(new ContentPath()), new MetadataFieldMapper[0], null);
38+
new RootObjectMapper.Builder("_doc").build(new ContentPath()), new MetadataFieldMapper[0], null);
4039

4140
private final RootObjectMapper root;
4241
private final Map<String, Object> meta;

server/src/main/java/org/elasticsearch/index/mapper/MappingLookup.java

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -129,7 +129,7 @@ private MappingLookup(Mapping mapping,
129129
if (objects.put(mapper.fullPath(), mapper) != null) {
130130
throw new MapperParsingException("Object mapper [" + mapper.fullPath() + "] is defined more than once");
131131
}
132-
if (mapper.nested().isNested()) {
132+
if (mapper.isNested()) {
133133
hasNested = true;
134134
}
135135
}
@@ -259,7 +259,7 @@ private void checkFieldNameLengthLimit(long limit) {
259259
private void checkNestedLimit(long limit) {
260260
long actualNestedFields = 0;
261261
for (ObjectMapper objectMapper : objectMappers.values()) {
262-
if (objectMapper.nested().isNested()) {
262+
if (objectMapper.isNested()) {
263263
actualNestedFields++;
264264
}
265265
}
@@ -288,7 +288,7 @@ public boolean isObjectField(String field) {
288288
public String getNestedScope(String path) {
289289
for (String parentPath = parentObject(path); parentPath != null; parentPath = parentObject(parentPath)) {
290290
ObjectMapper objectMapper = objectMappers.get(parentPath);
291-
if (objectMapper != null && objectMapper.nested().isNested()) {
291+
if (objectMapper != null && objectMapper.isNested()) {
292292
return parentPath;
293293
}
294294
}
@@ -369,13 +369,13 @@ public Mapping getMapping() {
369369
/**
370370
* Returns all nested object mappers
371371
*/
372-
public List<ObjectMapper> getNestedMappers() {
373-
List<ObjectMapper> childMappers = new ArrayList<>();
372+
public List<NestedObjectMapper> getNestedMappers() {
373+
List<NestedObjectMapper> childMappers = new ArrayList<>();
374374
for (ObjectMapper mapper : objectMappers().values()) {
375-
if (mapper.nested().isNested() == false) {
375+
if (mapper.isNested() == false) {
376376
continue;
377377
}
378-
childMappers.add(mapper);
378+
childMappers.add((NestedObjectMapper) mapper);
379379
}
380380
return childMappers;
381381
}
@@ -385,16 +385,16 @@ public List<ObjectMapper> getNestedMappers() {
385385
*
386386
* Used by BitSetProducerWarmer
387387
*/
388-
public List<ObjectMapper> getNestedParentMappers() {
389-
List<ObjectMapper> parents = new ArrayList<>();
388+
public List<NestedObjectMapper> getNestedParentMappers() {
389+
List<NestedObjectMapper> parents = new ArrayList<>();
390390
for (ObjectMapper mapper : objectMappers().values()) {
391391
String nestedParentPath = getNestedParent(mapper.fullPath());
392392
if (nestedParentPath == null) {
393393
continue;
394394
}
395395
ObjectMapper parent = objectMappers().get(nestedParentPath);
396-
if (parent.nested().isNested()) {
397-
parents.add(parent);
396+
if (parent.isNested()) {
397+
parents.add((NestedObjectMapper)parent);
398398
}
399399
}
400400
return parents;
@@ -421,7 +421,7 @@ public String getNestedParent(String path) {
421421
if (mapper == null) {
422422
return null;
423423
}
424-
if (mapper.nested().isNested()) {
424+
if (mapper.isNested()) {
425425
return path;
426426
}
427427
if (path.contains(".") == false) {

0 commit comments

Comments
 (0)