Skip to content

Commit

Permalink
Return both concrete fields and aliases in DocumentFieldMappers#getMa…
Browse files Browse the repository at this point in the history
…pper. (elastic#31671)
  • Loading branch information
jtibshirani committed Jul 24, 2018
1 parent 44afa78 commit 9f5e204
Show file tree
Hide file tree
Showing 47 changed files with 579 additions and 362 deletions.
2 changes: 1 addition & 1 deletion docs/reference/mapping/types/alias.asciidoc
Original file line number Diff line number Diff line change
Expand Up @@ -74,7 +74,7 @@ field alias to query over multiple target fields in a single clause.
==== Unsupported APIs

Writes to field aliases are not supported: attempting to use an alias in an index or update request
will result in a failure.
will result in a failure. This also precludes aliases from being the target of `copy_to`.

Because alias names are not present in the document source, aliases cannot be used when performing
source filtering. For example, the following request will return an empty result for `_source`:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -194,6 +194,10 @@ Query getCandidateMatchesQuery() {
return candidateMatchesQuery;
}

Query getVerifiedMatchesQuery() {
return verifiedMatchesQuery;
}

// Comparing identity here to avoid being cached
// Note that in theory if the same instance gets used multiple times it could still get cached,
// however since we create a new query instance each time we this query this shouldn't happen and thus
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -634,13 +634,13 @@ protected Analyzer getWrappedAnalyzer(String fieldName) {
docSearcher.setQueryCache(null);
}

PercolatorFieldMapper percolatorFieldMapper = (PercolatorFieldMapper) docMapper.mappers().getMapper(field);
boolean mapUnmappedFieldsAsString = percolatorFieldMapper.isMapUnmappedFieldAsText();
PercolatorFieldMapper.FieldType pft = (PercolatorFieldMapper.FieldType) fieldType;
String name = this.name != null ? this.name : pft.name();
QueryShardContext percolateShardContext = wrap(context);
PercolateQuery.QueryStore queryStore = createStore(pft.queryBuilderField,
percolateShardContext,
pft.mapUnmappedFieldsAsText);

String name = this.name != null ? this.name : field;
PercolatorFieldMapper.FieldType pft = (PercolatorFieldMapper.FieldType) fieldType;
PercolateQuery.QueryStore queryStore = createStore(pft.queryBuilderField, percolateShardContext, mapUnmappedFieldsAsString);
return pft.percolateQuery(name, queryStore, documents, docSearcher, context.indexVersionCreated());
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -142,13 +142,32 @@ public PercolatorFieldMapper build(BuilderContext context) {
fieldType.rangeField = rangeFieldMapper.fieldType();
NumberFieldMapper minimumShouldMatchFieldMapper = createMinimumShouldMatchField(context);
fieldType.minimumShouldMatchField = minimumShouldMatchFieldMapper.fieldType();
fieldType.mapUnmappedFieldsAsText = getMapUnmappedFieldAsText(context.indexSettings());

context.path().remove();
setupFieldType(context);
return new PercolatorFieldMapper(name(), fieldType, defaultFieldType, context.indexSettings(),
multiFieldsBuilder.build(this, context), copyTo, queryShardContext, extractedTermsField,
extractionResultField, queryBuilderField, rangeFieldMapper, minimumShouldMatchFieldMapper);
}

private static boolean getMapUnmappedFieldAsText(Settings indexSettings) {
if (INDEX_MAP_UNMAPPED_FIELDS_AS_TEXT_SETTING.exists(indexSettings) &&
INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.exists(indexSettings)) {
throw new IllegalArgumentException("Either specify [" + INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.getKey() +
"] or [" + INDEX_MAP_UNMAPPED_FIELDS_AS_TEXT_SETTING.getKey() + "] setting, not both");
}

if (INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.exists(indexSettings)) {
DEPRECATION_LOGGER.deprecatedAndMaybeLog(INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.getKey(),
"The [" + INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.getKey() +
"] setting is deprecated in favour for the [" + INDEX_MAP_UNMAPPED_FIELDS_AS_TEXT_SETTING.getKey() + "] setting");
return INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.get(indexSettings);
} else {
return INDEX_MAP_UNMAPPED_FIELDS_AS_TEXT_SETTING.get(indexSettings);
}
}

static KeywordFieldMapper createExtractQueryFieldBuilder(String name, BuilderContext context) {
KeywordFieldMapper.Builder queryMetaDataFieldBuilder = new KeywordFieldMapper.Builder(name);
queryMetaDataFieldBuilder.docValues(false);
Expand Down Expand Up @@ -201,6 +220,7 @@ static class FieldType extends MappedFieldType {
MappedFieldType minimumShouldMatchField;

RangeFieldMapper.RangeFieldType rangeField;
boolean mapUnmappedFieldsAsText;

FieldType() {
setIndexOptions(IndexOptions.NONE);
Expand All @@ -215,6 +235,7 @@ static class FieldType extends MappedFieldType {
queryBuilderField = ref.queryBuilderField;
rangeField = ref.rangeField;
minimumShouldMatchField = ref.minimumShouldMatchField;
mapUnmappedFieldsAsText = ref.mapUnmappedFieldsAsText;
}

@Override
Expand Down Expand Up @@ -333,7 +354,6 @@ Tuple<List<BytesRef>, Map<String, List<byte[]>>> extractTermsAndRanges(IndexRead

}

private final boolean mapUnmappedFieldAsText;
private final Supplier<QueryShardContext> queryShardContext;
private KeywordFieldMapper queryTermsField;
private KeywordFieldMapper extractionResultField;
Expand All @@ -354,27 +374,9 @@ Tuple<List<BytesRef>, Map<String, List<byte[]>>> extractTermsAndRanges(IndexRead
this.extractionResultField = extractionResultField;
this.queryBuilderField = queryBuilderField;
this.minimumShouldMatchFieldMapper = minimumShouldMatchFieldMapper;
this.mapUnmappedFieldAsText = getMapUnmappedFieldAsText(indexSettings);
this.rangeFieldMapper = rangeFieldMapper;
}

private static boolean getMapUnmappedFieldAsText(Settings indexSettings) {
if (INDEX_MAP_UNMAPPED_FIELDS_AS_TEXT_SETTING.exists(indexSettings) &&
INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.exists(indexSettings)) {
throw new IllegalArgumentException("Either specify [" + INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.getKey() +
"] or [" + INDEX_MAP_UNMAPPED_FIELDS_AS_TEXT_SETTING.getKey() + "] setting, not both");
}

if (INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.exists(indexSettings)) {
DEPRECATION_LOGGER.deprecatedAndMaybeLog(INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.getKey(),
"The [" + INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.getKey() +
"] setting is deprecated in favour for the [" + INDEX_MAP_UNMAPPED_FIELDS_AS_TEXT_SETTING.getKey() + "] setting");
return INDEX_MAP_UNMAPPED_FIELDS_AS_STRING_SETTING.get(indexSettings);
} else {
return INDEX_MAP_UNMAPPED_FIELDS_AS_TEXT_SETTING.get(indexSettings);
}
}

@Override
public FieldMapper updateFieldType(Map<String, MappedFieldType> fullNameToFieldType) {
PercolatorFieldMapper updated = (PercolatorFieldMapper) super.updateFieldType(fullNameToFieldType);
Expand Down Expand Up @@ -421,7 +423,7 @@ public Mapper parse(ParseContext context) throws IOException {

Version indexVersion = context.mapperService().getIndexSettings().getIndexVersionCreated();
createQueryBuilderField(indexVersion, queryBuilderField, queryBuilder, context);
Query query = toQuery(queryShardContext, mapUnmappedFieldAsText, queryBuilder);
Query query = toQuery(queryShardContext, isMapUnmappedFieldAsText(), queryBuilder);
processQuery(query, context);
return null;
}
Expand Down Expand Up @@ -541,7 +543,7 @@ protected String contentType() {
}

boolean isMapUnmappedFieldAsText() {
return mapUnmappedFieldAsText;
return ((FieldType) fieldType).mapUnmappedFieldsAsText;
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -194,8 +194,7 @@ public void testDuel() throws Exception {
}
Collections.sort(intValues);

MappedFieldType intFieldType = mapperService.documentMapper("type").mappers()
.getMapper("int_field").fieldType();
MappedFieldType intFieldType = mapperService.fullName("int_field");

List<Supplier<Query>> queryFunctions = new ArrayList<>();
queryFunctions.add(MatchNoDocsQuery::new);
Expand Down Expand Up @@ -327,8 +326,7 @@ public void testDuel2() throws Exception {
stringValues.add("value2");
stringValues.add("value3");

MappedFieldType intFieldType = mapperService.documentMapper("type").mappers()
.getMapper("int_field").fieldType();
MappedFieldType intFieldType = mapperService.fullName("int_field");
List<int[]> ranges = new ArrayList<>();
ranges.add(new int[]{-5, 5});
ranges.add(new int[]{0, 10});
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,8 @@ public class PercolateQueryBuilderTests extends AbstractQueryTestCase<PercolateQ
PercolateQueryBuilder.DOCUMENTS_FIELD.getPreferredName()
};

private static String queryField;
private static String queryField = "field";
private static String aliasField = "alias";
private static String docType;

private String indexedDocumentIndex;
Expand All @@ -96,9 +97,11 @@ protected Collection<Class<? extends Plugin>> getPlugins() {
@Override
protected void initializeAdditionalMappings(MapperService mapperService) throws IOException {
queryField = randomAlphaOfLength(4);
aliasField = randomAlphaOfLength(4);

String docType = "_doc";
mapperService.merge(docType, new CompressedXContent(Strings.toString(PutMappingRequest.buildFromSimplifiedDef(docType,
queryField, "type=percolator"
queryField, "type=percolator", aliasField, "type=alias,path=" + queryField
))), MapperService.MergeReason.MAPPING_UPDATE, false);
mapperService.merge(docType, new CompressedXContent(Strings.toString(PutMappingRequest.buildFromSimplifiedDef(docType,
STRING_FIELD_NAME, "type=text"
Expand Down Expand Up @@ -364,4 +367,22 @@ public void testSerializationFailsUnlessFetched() throws IOException {
builder = rewriteAndFetch(builder, createShardContext());
builder.writeTo(new BytesStreamOutput(10));
}

public void testFieldAlias() throws IOException {
QueryShardContext shardContext = createShardContext();

PercolateQueryBuilder builder = doCreateTestQueryBuilder(false);
QueryBuilder rewrittenBuilder = rewriteAndFetch(builder, shardContext);
PercolateQuery query = (PercolateQuery) rewrittenBuilder.toQuery(shardContext);

PercolateQueryBuilder aliasBuilder = new PercolateQueryBuilder(aliasField,
builder.getDocumentType(),
builder.getDocuments(),
builder.getXContentType());
QueryBuilder rewrittenAliasBuilder = rewriteAndFetch(aliasBuilder, shardContext);
PercolateQuery aliasQuery = (PercolateQuery) rewrittenAliasBuilder.toQuery(shardContext);

assertEquals(query.getCandidateMatchesQuery(), aliasQuery.getCandidateMatchesQuery());
assertEquals(query.getVerifiedMatchesQuery(), aliasQuery.getVerifiedMatchesQuery());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -224,10 +224,10 @@ public void testExtractTerms() throws Exception {
public void testExtractRanges() throws Exception {
addQueryFieldMappings();
BooleanQuery.Builder bq = new BooleanQuery.Builder();
Query rangeQuery1 = mapperService.documentMapper("doc").mappers().getMapper("number_field1").fieldType()
Query rangeQuery1 = mapperService.fullName("number_field1")
.rangeQuery(10, 20, true, true, null, null, null, null);
bq.add(rangeQuery1, Occur.MUST);
Query rangeQuery2 = mapperService.documentMapper("doc").mappers().getMapper("number_field1").fieldType()
Query rangeQuery2 = mapperService.fullName("number_field1")
.rangeQuery(15, 20, true, true, null, null, null, null);
bq.add(rangeQuery2, Occur.MUST);

Expand Down Expand Up @@ -255,7 +255,7 @@ public void testExtractRanges() throws Exception {
// Range queries on different fields:
bq = new BooleanQuery.Builder();
bq.add(rangeQuery1, Occur.MUST);
rangeQuery2 = mapperService.documentMapper("doc").mappers().getMapper("number_field2").fieldType()
rangeQuery2 = mapperService.fullName("number_field2")
.rangeQuery(15, 20, true, true, null, null, null, null);
bq.add(rangeQuery2, Occur.MUST);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@
import org.elasticsearch.index.IndexService;
import org.elasticsearch.index.mapper.DocumentFieldMappers;
import org.elasticsearch.index.mapper.DocumentMapper;
import org.elasticsearch.index.mapper.FieldMapper;
import org.elasticsearch.index.mapper.Mapper;
import org.elasticsearch.index.shard.ShardId;
import org.elasticsearch.indices.IndicesService;
import org.elasticsearch.indices.TypeMissingException;
Expand Down Expand Up @@ -175,19 +175,19 @@ private static Map<String, FieldMappingMetaData> findFieldMappingsByType(Predica
final DocumentFieldMappers allFieldMappers = documentMapper.mappers();
for (String field : request.fields()) {
if (Regex.isMatchAllPattern(field)) {
for (FieldMapper fieldMapper : allFieldMappers) {
addFieldMapper(fieldPredicate, fieldMapper.fieldType().name(), fieldMapper, fieldMappings, request.includeDefaults());
for (Mapper fieldMapper : allFieldMappers) {
addFieldMapper(fieldPredicate, fieldMapper.name(), fieldMapper, fieldMappings, request.includeDefaults());
}
} else if (Regex.isSimpleMatchPattern(field)) {
for (FieldMapper fieldMapper : allFieldMappers) {
if (Regex.simpleMatch(field, fieldMapper.fieldType().name())) {
addFieldMapper(fieldPredicate, fieldMapper.fieldType().name(),
for (Mapper fieldMapper : allFieldMappers) {
if (Regex.simpleMatch(field, fieldMapper.name())) {
addFieldMapper(fieldPredicate, fieldMapper.name(),
fieldMapper, fieldMappings, request.includeDefaults());
}
}
} else {
// not a pattern
FieldMapper fieldMapper = allFieldMappers.getMapper(field);
Mapper fieldMapper = allFieldMappers.getMapper(field);
if (fieldMapper != null) {
addFieldMapper(fieldPredicate, field, fieldMapper, fieldMappings, request.includeDefaults());
} else if (request.probablySingleFieldRequest()) {
Expand All @@ -199,7 +199,7 @@ private static Map<String, FieldMappingMetaData> findFieldMappingsByType(Predica
}

private static void addFieldMapper(Predicate<String> fieldPredicate,
String field, FieldMapper fieldMapper, Map<String, FieldMappingMetaData> fieldMappings,
String field, Mapper fieldMapper, Map<String, FieldMappingMetaData> fieldMappings,
boolean includeDefaults) {
if (fieldMappings.containsKey(field)) {
return;
Expand All @@ -208,7 +208,7 @@ private static void addFieldMapper(Predicate<String> fieldPredicate,
try {
BytesReference bytes = XContentHelper.toXContent(fieldMapper, XContentType.JSON,
includeDefaults ? includeDefaultsParams : ToXContent.EMPTY_PARAMS, false);
fieldMappings.put(field, new FieldMappingMetaData(fieldMapper.fieldType().name(), bytes));
fieldMappings.put(field, new FieldMappingMetaData(fieldMapper.name(), bytes));
} catch (IOException e) {
throw new ElasticsearchException("failed to serialize XContent of field [" + field + "]", e);
}
Expand Down
16 changes: 6 additions & 10 deletions server/src/main/java/org/elasticsearch/index/IndexWarmer.java
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,6 @@
import org.elasticsearch.index.engine.Engine;
import org.elasticsearch.index.fielddata.IndexFieldData;
import org.elasticsearch.index.fielddata.IndexFieldDataService;
import org.elasticsearch.index.mapper.DocumentMapper;
import org.elasticsearch.index.mapper.FieldMapper;
import org.elasticsearch.index.mapper.MappedFieldType;
import org.elasticsearch.index.mapper.MapperService;
import org.elasticsearch.index.shard.IndexShard;
Expand Down Expand Up @@ -121,15 +119,13 @@ private static class FieldDataWarmer implements IndexWarmer.Listener {
public TerminationHandle warmReader(final IndexShard indexShard, final Engine.Searcher searcher) {
final MapperService mapperService = indexShard.mapperService();
final Map<String, MappedFieldType> warmUpGlobalOrdinals = new HashMap<>();
for (DocumentMapper docMapper : mapperService.docMappers(false)) {
for (FieldMapper fieldMapper : docMapper.mappers()) {
final MappedFieldType fieldType = fieldMapper.fieldType();
final String indexName = fieldType.name();
if (fieldType.eagerGlobalOrdinals() == false) {
continue;
}
warmUpGlobalOrdinals.put(indexName, fieldType);

for (MappedFieldType fieldType : mapperService.fieldTypes()) {
final String indexName = fieldType.name();
if (fieldType.eagerGlobalOrdinals() == false) {
continue;
}
warmUpGlobalOrdinals.put(indexName, fieldType);
}
final CountDownLatch latch = new CountDownLatch(warmUpGlobalOrdinals.size());
for (final MappedFieldType fieldType : warmUpGlobalOrdinals.values()) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@
import org.elasticsearch.index.fieldvisitor.CustomFieldsVisitor;
import org.elasticsearch.index.fieldvisitor.FieldsVisitor;
import org.elasticsearch.index.mapper.DocumentMapper;
import org.elasticsearch.index.mapper.FieldMapper;
import org.elasticsearch.index.mapper.Mapper;
import org.elasticsearch.index.mapper.MapperService;
import org.elasticsearch.index.mapper.ParentFieldMapper;
import org.elasticsearch.index.mapper.RoutingFieldMapper;
Expand Down Expand Up @@ -218,7 +218,7 @@ private GetResult innerGetLoadFromStoredFields(String type, String id, String[]

if (gFields != null && gFields.length > 0) {
for (String field : gFields) {
FieldMapper fieldMapper = docMapper.mappers().getMapper(field);
Mapper fieldMapper = docMapper.mappers().getMapper(field);
if (fieldMapper == null) {
if (docMapper.objectMappers().get(field) != null) {
// Only fail if we know it is a object field, missing paths / fields shouldn't fail.
Expand Down
Loading

0 comments on commit 9f5e204

Please sign in to comment.