Skip to content

Commit bda4de6

Browse files
committed
Use fallback synthetic source for copy_to and doc_values: false cases
1 parent 19c044d commit bda4de6

File tree

69 files changed

+806
-914
lines changed

Some content is hidden

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

69 files changed

+806
-914
lines changed

modules/data-streams/src/javaRestTest/java/org/elasticsearch/datastreams/logsdb/LogsIndexModeCustomSettingsIT.java

Lines changed: 0 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -283,35 +283,6 @@ public void testOverrideIgnoreDynamicBeyondLimit() throws IOException {
283283
assertThat(ignoreDynamicBeyondLimitIndexSetting, equalTo("false"));
284284
}
285285

286-
public void testAddNonCompatibleMapping() throws IOException {
287-
var nonCompatibleMappingAdditionTemplate = """
288-
{
289-
"template": {
290-
"mappings": {
291-
"properties": {
292-
"bomb": {
293-
"type": "ip",
294-
"doc_values": false
295-
}
296-
}
297-
}
298-
}
299-
}""";
300-
301-
Exception e = assertThrows(
302-
ResponseException.class,
303-
() -> putComponentTemplate(client, "logs@custom", nonCompatibleMappingAdditionTemplate)
304-
);
305-
assertThat(
306-
e.getMessage(),
307-
containsString("updating component template [logs@custom] results in invalid composable template [logs]")
308-
);
309-
assertThat(
310-
e.getMessage(),
311-
containsString("field [bomb] of type [ip] doesn't support synthetic source because it doesn't have doc values")
312-
);
313-
}
314-
315286
private static Map<String, Object> getMapping(final RestClient client, final String indexName) throws IOException {
316287
final Request request = new Request("GET", "/" + indexName + "/_mapping");
317288

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

Lines changed: 4 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,6 @@
4545
import org.elasticsearch.index.mapper.DocumentParserContext;
4646
import org.elasticsearch.index.mapper.FieldMapper;
4747
import org.elasticsearch.index.mapper.MapperBuilderContext;
48-
import org.elasticsearch.index.mapper.SourceLoader;
4948
import org.elasticsearch.index.mapper.SourceValueFetcher;
5049
import org.elasticsearch.index.mapper.StringFieldType;
5150
import org.elasticsearch.index.mapper.StringStoredFieldFieldLoader;
@@ -436,22 +435,14 @@ public MatchOnlyTextFieldType fieldType() {
436435
}
437436

438437
@Override
439-
protected SyntheticSourceMode syntheticSourceMode() {
440-
return SyntheticSourceMode.NATIVE;
441-
}
442-
443-
@Override
444-
public SourceLoader.SyntheticFieldLoader syntheticFieldLoader() {
445-
if (copyTo.copyToFields().isEmpty() != true) {
446-
throw new IllegalArgumentException(
447-
"field [" + fullPath() + "] of type [" + typeName() + "] doesn't support synthetic source because it declares copy_to"
448-
);
449-
}
450-
return new StringStoredFieldFieldLoader(fieldType().storedFieldNameForSyntheticSource(), leafName()) {
438+
protected SyntheticSourceSupport syntheticSourceSupport() {
439+
var loader = new StringStoredFieldFieldLoader(fieldType().storedFieldNameForSyntheticSource(), leafName()) {
451440
@Override
452441
protected void write(XContentBuilder b, Object value) throws IOException {
453442
b.value((String) value);
454443
}
455444
};
445+
446+
return new SyntheticSourceSupport.Native(loader);
456447
}
457448
}

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

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,6 @@
1212
import org.apache.lucene.search.Query;
1313
import org.elasticsearch.index.mapper.MappedFieldType;
1414
import org.elasticsearch.index.mapper.MetadataFieldMapper;
15-
import org.elasticsearch.index.mapper.SourceLoader;
1615
import org.elasticsearch.index.mapper.TextSearchInfo;
1716
import org.elasticsearch.index.mapper.ValueFetcher;
1817
import org.elasticsearch.index.query.SearchExecutionContext;
@@ -75,9 +74,4 @@ private RankFeatureMetaFieldMapper() {
7574
protected String contentType() {
7675
return CONTENT_TYPE;
7776
}
78-
79-
@Override
80-
public SourceLoader.SyntheticFieldLoader syntheticFieldLoader() {
81-
return SourceLoader.SyntheticFieldLoader.NOTHING;
82-
}
8377
}

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

Lines changed: 11 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,6 @@
3838
import org.elasticsearch.index.mapper.NumberFieldMapper;
3939
import org.elasticsearch.index.mapper.SimpleMappedFieldType;
4040
import org.elasticsearch.index.mapper.SortedNumericDocValuesSyntheticFieldLoader;
41-
import org.elasticsearch.index.mapper.SourceLoader;
4241
import org.elasticsearch.index.mapper.SourceValueFetcher;
4342
import org.elasticsearch.index.mapper.TextSearchInfo;
4443
import org.elasticsearch.index.mapper.TimeSeriesParams;
@@ -713,32 +712,19 @@ public int docValueCount() {
713712
}
714713

715714
@Override
716-
protected SyntheticSourceMode syntheticSourceMode() {
717-
return SyntheticSourceMode.NATIVE;
718-
}
715+
protected SyntheticSourceSupport syntheticSourceSupport() {
716+
if (hasDocValues) {
717+
var loader = new SortedNumericDocValuesSyntheticFieldLoader(fullPath(), leafName(), ignoreMalformed.value()) {
718+
@Override
719+
protected void writeValue(XContentBuilder b, long value) throws IOException {
720+
b.value(decodeForSyntheticSource(value, scalingFactor));
721+
}
722+
};
719723

720-
@Override
721-
public SourceLoader.SyntheticFieldLoader syntheticFieldLoader() {
722-
if (hasDocValues == false) {
723-
throw new IllegalArgumentException(
724-
"field ["
725-
+ fullPath()
726-
+ "] of type ["
727-
+ typeName()
728-
+ "] doesn't support synthetic source because it doesn't have doc values"
729-
);
730-
}
731-
if (copyTo.copyToFields().isEmpty() != true) {
732-
throw new IllegalArgumentException(
733-
"field [" + fullPath() + "] of type [" + typeName() + "] doesn't support synthetic source because it declares copy_to"
734-
);
724+
return new SyntheticSourceSupport.Native(loader);
735725
}
736-
return new SortedNumericDocValuesSyntheticFieldLoader(fullPath(), leafName(), ignoreMalformed.value()) {
737-
@Override
738-
protected void writeValue(XContentBuilder b, long value) throws IOException {
739-
b.value(decodeForSyntheticSource(value, scalingFactor));
740-
}
741-
};
726+
727+
return super.syntheticSourceSupport();
742728
}
743729

744730
/**

modules/mapper-extras/src/test/java/org/elasticsearch/index/mapper/extras/ScaledFloatFieldMapperTests.java

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -470,12 +470,7 @@ private void mapping(XContentBuilder b) throws IOException {
470470

471471
@Override
472472
public List<SyntheticSourceInvalidExample> invalidExample() throws IOException {
473-
return List.of(
474-
new SyntheticSourceInvalidExample(
475-
equalTo("field [field] of type [scaled_float] doesn't support synthetic source because it doesn't have doc values"),
476-
b -> b.field("type", "scaled_float").field("scaling_factor", 10).field("doc_values", false)
477-
)
478-
);
473+
return List.of();
479474
}
480475
}
481476

modules/mapper-extras/src/yamlRestTest/resources/rest-api-spec/test/match_only_text/10_basic.yml

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -351,3 +351,45 @@ tsdb:
351351
"@timestamp" : "2000-01-01T00:00:00.000Z"
352352
"dimension" : "a"
353353
foo: "Apache Lucene powers Elasticsearch"
354+
355+
---
356+
synthetic_source with copy_to:
357+
- requires:
358+
cluster_features: ["mapper.source.synthetic_source_restrictions_removed"]
359+
reason: requires copy_to support in synthetic source
360+
361+
- do:
362+
indices.create:
363+
index: synthetic_source_test
364+
body:
365+
mappings:
366+
_source:
367+
mode: synthetic
368+
properties:
369+
foo:
370+
type: match_only_text
371+
copy_to: copy
372+
copy:
373+
type: keyword
374+
375+
- do:
376+
index:
377+
index: synthetic_source_test
378+
id: "1"
379+
refresh: true
380+
body:
381+
foo: "Apache Lucene powers Elasticsearch"
382+
383+
- do:
384+
search:
385+
index: synthetic_source_test
386+
body:
387+
fields: ["copy"]
388+
389+
- match: { "hits.total.value": 1 }
390+
- match:
391+
hits.hits.0._source.foo: "Apache Lucene powers Elasticsearch"
392+
- match:
393+
hits.hits.0.fields.copy.0: "Apache Lucene powers Elasticsearch"
394+
395+

plugins/mapper-annotated-text/src/main/java/org/elasticsearch/index/mapper/annotatedtext/AnnotatedTextFieldMapper.java

Lines changed: 6 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,6 @@
3030
import org.elasticsearch.index.mapper.FieldMapper;
3131
import org.elasticsearch.index.mapper.KeywordFieldMapper;
3232
import org.elasticsearch.index.mapper.MapperBuilderContext;
33-
import org.elasticsearch.index.mapper.SourceLoader;
3433
import org.elasticsearch.index.mapper.StringStoredFieldFieldLoader;
3534
import org.elasticsearch.index.mapper.TextFieldMapper;
3635
import org.elasticsearch.index.mapper.TextParams;
@@ -46,7 +45,6 @@
4645
import java.nio.charset.StandardCharsets;
4746
import java.util.ArrayList;
4847
import java.util.List;
49-
import java.util.Locale;
5048
import java.util.Map;
5149
import java.util.regex.Matcher;
5250
import java.util.regex.Pattern;
@@ -572,39 +570,23 @@ public FieldMapper.Builder getMergeBuilder() {
572570
}
573571

574572
@Override
575-
protected SyntheticSourceMode syntheticSourceMode() {
576-
return SyntheticSourceMode.NATIVE;
577-
}
578-
579-
@Override
580-
public SourceLoader.SyntheticFieldLoader syntheticFieldLoader() {
581-
if (copyTo.copyToFields().isEmpty() != true) {
582-
throw new IllegalArgumentException(
583-
"field [" + fullPath() + "] of type [" + typeName() + "] doesn't support synthetic source because it declares copy_to"
584-
);
585-
}
573+
protected SyntheticSourceSupport syntheticSourceSupport() {
586574
if (fieldType.stored()) {
587-
return new StringStoredFieldFieldLoader(fullPath(), leafName()) {
575+
var loader = new StringStoredFieldFieldLoader(fullPath(), leafName()) {
588576
@Override
589577
protected void write(XContentBuilder b, Object value) throws IOException {
590578
b.value((String) value);
591579
}
592580
};
581+
582+
return new SyntheticSourceSupport.Native(loader);
593583
}
594584

595585
var kwd = TextFieldMapper.SyntheticSourceHelper.getKeywordFieldMapperForSyntheticSource(this);
596586
if (kwd != null) {
597-
return kwd.syntheticFieldLoader(leafName());
587+
return new SyntheticSourceSupport.Native(kwd.syntheticFieldLoader(leafName()));
598588
}
599589

600-
throw new IllegalArgumentException(
601-
String.format(
602-
Locale.ROOT,
603-
"field [%s] of type [%s] doesn't support synthetic source unless it is stored or has a sub-field of"
604-
+ " type [keyword] with doc values or stored and without a normalizer",
605-
fullPath(),
606-
typeName()
607-
)
608-
);
590+
return super.syntheticSourceSupport();
609591
}
610592
}

plugins/mapper-annotated-text/src/yamlRestTest/resources/rest-api-spec/test/mapper_annotatedtext/20_synthetic_source.yml

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -195,3 +195,34 @@ multiple values in stored annotated_text field with keyword multi-field:
195195
- match:
196196
hits.hits.0._source:
197197
annotated_text: ["world", "hello", "world"]
198+
199+
---
200+
fallback synthetic source:
201+
- do:
202+
indices.create:
203+
index: test
204+
body:
205+
mappings:
206+
_source:
207+
mode: synthetic
208+
properties:
209+
annotated_text:
210+
type: annotated_text
211+
store: false
212+
213+
- do:
214+
index:
215+
index: test
216+
id: 1
217+
refresh: true
218+
body:
219+
annotated_text: ["world", "hello", "world"]
220+
221+
- do:
222+
search:
223+
index: test
224+
225+
- match:
226+
hits.hits.0._source:
227+
annotated_text: ["world", "hello", "world"]
228+

plugins/mapper-size/src/main/java/org/elasticsearch/index/mapper/size/SizeFieldMapper.java

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,6 @@
1616
import org.elasticsearch.index.mapper.MetadataFieldMapper;
1717
import org.elasticsearch.index.mapper.NumberFieldMapper.NumberFieldType;
1818
import org.elasticsearch.index.mapper.NumberFieldMapper.NumberType;
19-
import org.elasticsearch.index.mapper.SourceLoader;
2019
import org.elasticsearch.index.mapper.ValueFetcher;
2120
import org.elasticsearch.index.query.SearchExecutionContext;
2221

@@ -97,9 +96,4 @@ public void postParse(DocumentParserContext context) {
9796
public FieldMapper.Builder getMergeBuilder() {
9897
return new Builder().init(this);
9998
}
100-
101-
@Override
102-
public SourceLoader.SyntheticFieldLoader syntheticFieldLoader() {
103-
return SourceLoader.SyntheticFieldLoader.NOTHING;
104-
}
10599
}

rest-api-spec/src/yamlRestTest/resources/rest-api-spec/test/get/100_synthetic_source.yml

Lines changed: 0 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1040,25 +1040,6 @@ flattened field:
10401040

10411041
- is_false: fields
10421042

1043-
---
1044-
flattened field no doc values:
1045-
- requires:
1046-
cluster_features: ["gte_v8.8.0"]
1047-
reason: support for synthetic source on flattened fields added in 8.8.0
1048-
1049-
- do:
1050-
catch: /field \[flattened\] of type \[flattened\] doesn't support synthetic source because it doesn't have doc values/
1051-
indices.create:
1052-
index: test
1053-
body:
1054-
mappings:
1055-
_source:
1056-
mode: synthetic
1057-
properties:
1058-
flattened:
1059-
type: flattened
1060-
doc_values: false
1061-
10621043
---
10631044
flattened field with ignore_above:
10641045
- requires:

0 commit comments

Comments
 (0)