Skip to content

Commit b4625e0

Browse files
committed
Fix match_only_text for keyword multi-fields with doc values and ignore above
1 parent 20604d6 commit b4625e0

File tree

1 file changed

+47
-7
lines changed

1 file changed

+47
-7
lines changed

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

Lines changed: 47 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -253,11 +253,18 @@ private IOFunction<LeafReaderContext, CheckedIntFunction<List<Object>, IOExcepti
253253
if (searchExecutionContext.isSourceSynthetic() && withinMultiField) {
254254
String parentField = searchExecutionContext.parentPath(name());
255255
var parent = searchExecutionContext.lookup().fieldType(parentField);
256-
if (parent.isStored()) {
257-
if (parent instanceof KeywordFieldMapper.KeywordFieldType keywordParent
258-
&& keywordParent.ignoreAbove() != Integer.MAX_VALUE) {
256+
257+
if (parent instanceof KeywordFieldMapper.KeywordFieldType keywordParent
258+
&& keywordParent.ignoreAbove() != Integer.MAX_VALUE) {
259+
if (parent.isStored()) {
259260
return storedFieldFetcher(parentField, keywordParent.originalName());
261+
} else if (parent.hasDocValues()) {
262+
var ifd = searchExecutionContext.getForField(parent, MappedFieldType.FielddataOperation.SEARCH);
263+
return combineFieldFetchers(docValuesFieldFetcher(ifd), storedFieldFetcher(keywordParent.originalName()));
260264
}
265+
}
266+
267+
if (parent.isStored()) {
261268
return storedFieldFetcher(parentField);
262269
} else if (parent.hasDocValues()) {
263270
var ifd = searchExecutionContext.getForField(parent, MappedFieldType.FielddataOperation.SEARCH);
@@ -268,14 +275,21 @@ private IOFunction<LeafReaderContext, CheckedIntFunction<List<Object>, IOExcepti
268275
} else if (searchExecutionContext.isSourceSynthetic() && hasCompatibleMultiFields) {
269276
var mapper = (MatchOnlyTextFieldMapper) searchExecutionContext.getMappingLookup().getMapper(name());
270277
var kwd = TextFieldMapper.SyntheticSourceHelper.getKeywordFieldMapperForSyntheticSource(mapper);
278+
271279
if (kwd != null) {
272280
var fieldType = kwd.fieldType();
273-
if (fieldType.isStored()) {
274-
if (fieldType.ignoreAbove() != Integer.MAX_VALUE) {
281+
282+
if (fieldType.ignoreAbove() != Integer.MAX_VALUE) {
283+
if (fieldType.isStored()) {
275284
return storedFieldFetcher(fieldType.name(), fieldType.originalName());
276-
} else {
277-
return storedFieldFetcher(fieldType.name());
285+
} else if (fieldType.hasDocValues()) {
286+
var ifd = searchExecutionContext.getForField(fieldType, MappedFieldType.FielddataOperation.SEARCH);
287+
return combineFieldFetchers(docValuesFieldFetcher(ifd), storedFieldFetcher(fieldType.originalName()));
278288
}
289+
}
290+
291+
if (fieldType.isStored()) {
292+
return storedFieldFetcher(fieldType.name());
279293
} else if (fieldType.hasDocValues()) {
280294
var ifd = searchExecutionContext.getForField(fieldType, MappedFieldType.FielddataOperation.SEARCH);
281295
return docValuesFieldFetcher(ifd);
@@ -337,6 +351,32 @@ private static IOFunction<LeafReaderContext, CheckedIntFunction<List<Object>, IO
337351
};
338352
}
339353

354+
private static IOFunction<LeafReaderContext, CheckedIntFunction<List<Object>, IOException>> combineFieldFetchers(
355+
IOFunction<LeafReaderContext, CheckedIntFunction<List<Object>, IOException>> primaryFetcher,
356+
IOFunction<LeafReaderContext, CheckedIntFunction<List<Object>, IOException>> secondaryFetcher
357+
) {
358+
return context -> {
359+
var primaryGetter = primaryFetcher.apply(context);
360+
var secondaryGetter = secondaryFetcher.apply(context);
361+
return docId -> {
362+
List<Object> values = new ArrayList<>();
363+
var primary = primaryGetter.apply(docId);
364+
if (primary != null) {
365+
values.addAll(primary);
366+
}
367+
368+
var secondary = secondaryGetter.apply(docId);
369+
if (secondary != null) {
370+
values.addAll(secondary);
371+
}
372+
373+
assert primary != null || secondary != null;
374+
375+
return values;
376+
};
377+
};
378+
}
379+
340380
private Query toQuery(Query query, SearchExecutionContext searchExecutionContext) {
341381
return new ConstantScoreQuery(
342382
new SourceConfirmedTextQuery(query, getValueFetcherProvider(searchExecutionContext), indexAnalyzer)

0 commit comments

Comments
 (0)