Skip to content

Commit 3b27f4d

Browse files
Changes to support IP field in star tree indexing (#16641) (#17122)
* Changes to support IP --------- (cherry picked from commit e6d71d2) Signed-off-by: bharath-techie <[email protected]> Signed-off-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com> Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>
1 parent bf42c3e commit 3b27f4d

File tree

13 files changed

+204
-43
lines changed

13 files changed

+204
-43
lines changed

server/src/internalClusterTest/java/org/opensearch/index/mapper/StarTreeMapperIT.java

Lines changed: 15 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@ public class StarTreeMapperIT extends OpenSearchIntegTestCase {
5656
.put(IndexSettings.INDEX_TRANSLOG_FLUSH_THRESHOLD_SIZE_SETTING.getKey(), new ByteSizeValue(512, ByteSizeUnit.MB))
5757
.build();
5858

59-
private static XContentBuilder createMinimalTestMapping(boolean invalidDim, boolean invalidMetric, boolean ipdim) {
59+
private static XContentBuilder createMinimalTestMapping(boolean invalidDim, boolean invalidMetric, boolean wildcard) {
6060
try {
6161
return jsonBuilder().startObject()
6262
.startObject("composite")
@@ -68,7 +68,7 @@ private static XContentBuilder createMinimalTestMapping(boolean invalidDim, bool
6868
.endObject()
6969
.startArray("ordered_dimensions")
7070
.startObject()
71-
.field("name", getDim(invalidDim, ipdim))
71+
.field("name", getDim(invalidDim, wildcard))
7272
.endObject()
7373
.startObject()
7474
.field("name", "keyword_dv")
@@ -102,8 +102,16 @@ private static XContentBuilder createMinimalTestMapping(boolean invalidDim, bool
102102
.field("type", "keyword")
103103
.field("doc_values", false)
104104
.endObject()
105+
.startObject("ip_no_dv")
106+
.field("type", "ip")
107+
.field("doc_values", false)
108+
.endObject()
105109
.startObject("ip")
106110
.field("type", "ip")
111+
.field("doc_values", true)
112+
.endObject()
113+
.startObject("wildcard")
114+
.field("type", "wildcard")
107115
.field("doc_values", false)
108116
.endObject()
109117
.endObject()
@@ -362,11 +370,11 @@ private XContentBuilder getMappingWithDuplicateFields(boolean isDuplicateDim, bo
362370
return mapping;
363371
}
364372

365-
private static String getDim(boolean hasDocValues, boolean isKeyword) {
373+
private static String getDim(boolean hasDocValues, boolean isWildCard) {
366374
if (hasDocValues) {
367-
return random().nextBoolean() ? "numeric" : "keyword";
368-
} else if (isKeyword) {
369-
return "ip";
375+
return random().nextBoolean() ? "numeric" : random().nextBoolean() ? "keyword" : "ip_no_dv";
376+
} else if (isWildCard) {
377+
return "wildcard";
370378
}
371379
return "numeric_dv";
372380
}
@@ -748,7 +756,7 @@ public void testUnsupportedDim() {
748756
() -> prepareCreate(TEST_INDEX).setSettings(settings).setMapping(createMinimalTestMapping(false, false, true)).get()
749757
);
750758
assertEquals(
751-
"Failed to parse mapping [_doc]: unsupported field type associated with dimension [ip] as part of star tree field [startree-1]",
759+
"Failed to parse mapping [_doc]: unsupported field type associated with dimension [wildcard] as part of star tree field [startree-1]",
752760
ex.getMessage()
753761
);
754762
}

server/src/main/java/org/opensearch/index/codec/composite/composite912/Composite912DocValuesWriter.java

Lines changed: 24 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -33,9 +33,11 @@
3333
import org.opensearch.index.compositeindex.datacube.startree.builder.StarTreesBuilder;
3434
import org.opensearch.index.compositeindex.datacube.startree.index.CompositeIndexValues;
3535
import org.opensearch.index.compositeindex.datacube.startree.index.StarTreeValues;
36+
import org.opensearch.index.fielddata.IndexNumericFieldData;
37+
import org.opensearch.index.fielddata.plain.SortedSetOrdinalsIndexFieldData;
3638
import org.opensearch.index.mapper.CompositeMappedFieldType;
3739
import org.opensearch.index.mapper.DocCountFieldMapper;
38-
import org.opensearch.index.mapper.KeywordFieldMapper;
40+
import org.opensearch.index.mapper.MappedFieldType;
3941
import org.opensearch.index.mapper.MapperService;
4042

4143
import java.io.IOException;
@@ -44,6 +46,7 @@
4446
import java.util.HashMap;
4547
import java.util.HashSet;
4648
import java.util.List;
49+
import java.util.Locale;
4750
import java.util.Map;
4851
import java.util.Set;
4952
import java.util.concurrent.atomic.AtomicInteger;
@@ -262,22 +265,38 @@ public SortedSetDocValues getSortedSet(FieldInfo field) {
262265
return DocValues.emptySortedSet();
263266
}
264267
});
265-
}
266-
// TODO : change this logic to evaluate for sortedNumericField specifically
267-
else {
268+
} else if (isSortedNumericField(compositeField)) {
268269
fieldProducerMap.put(compositeField, new EmptyDocValuesProducer() {
269270
@Override
270271
public SortedNumericDocValues getSortedNumeric(FieldInfo field) {
271272
return DocValues.emptySortedNumeric();
272273
}
273274
});
275+
} else {
276+
throw new IllegalStateException(
277+
String.format(Locale.ROOT, "Unsupported DocValues field associated with the composite field : %s", compositeField)
278+
);
274279
}
275280
}
276281
compositeFieldSet.remove(compositeField);
277282
}
278283

279284
private boolean isSortedSetField(String field) {
280-
return mapperService.fieldType(field) instanceof KeywordFieldMapper.KeywordFieldType;
285+
MappedFieldType ft = mapperService.fieldType(field);
286+
assert ft.isAggregatable();
287+
return ft.fielddataBuilder(
288+
"",
289+
() -> { throw new UnsupportedOperationException("SearchLookup not available"); }
290+
) instanceof SortedSetOrdinalsIndexFieldData.Builder;
291+
}
292+
293+
private boolean isSortedNumericField(String field) {
294+
MappedFieldType ft = mapperService.fieldType(field);
295+
assert ft.isAggregatable();
296+
return ft.fielddataBuilder(
297+
"",
298+
() -> { throw new UnsupportedOperationException("SearchLookup not available"); }
299+
) instanceof IndexNumericFieldData.Builder;
281300
}
282301

283302
@Override
@@ -370,5 +389,4 @@ private static SegmentWriteState getSegmentWriteState(SegmentWriteState segmentW
370389
segmentWriteState.segmentSuffix
371390
);
372391
}
373-
374392
}

server/src/main/java/org/opensearch/index/compositeindex/datacube/DimensionFactory.java

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,8 @@
2424
import java.util.stream.Collectors;
2525

2626
import static org.opensearch.index.compositeindex.datacube.DateDimension.CALENDAR_INTERVALS;
27-
import static org.opensearch.index.compositeindex.datacube.KeywordDimension.KEYWORD;
27+
import static org.opensearch.index.compositeindex.datacube.IpDimension.IP;
28+
import static org.opensearch.index.compositeindex.datacube.OrdinalDimension.ORDINAL;
2829

2930
/**
3031
* Dimension factory class mainly used to parse and create dimension from the mappings
@@ -44,8 +45,10 @@ public static Dimension parseAndCreateDimension(
4445
return parseAndCreateDateDimension(name, dimensionMap, c);
4546
case NumericDimension.NUMERIC:
4647
return new NumericDimension(name);
47-
case KEYWORD:
48-
return new KeywordDimension(name);
48+
case ORDINAL:
49+
return new OrdinalDimension(name);
50+
case IP:
51+
return new IpDimension(name);
4952
default:
5053
throw new IllegalArgumentException(
5154
String.format(Locale.ROOT, "unsupported field type associated with dimension [%s] as part of star tree field", name)
@@ -69,8 +72,10 @@ public static Dimension parseAndCreateDimension(
6972
return parseAndCreateDateDimension(name, dimensionMap, c);
7073
case NUMERIC:
7174
return new NumericDimension(name);
72-
case KEYWORD:
73-
return new KeywordDimension(name);
75+
case ORDINAL:
76+
return new OrdinalDimension(name);
77+
case IP:
78+
return new IpDimension(name);
7479
default:
7580
throw new IllegalArgumentException(
7681
String.format(Locale.ROOT, "unsupported field type associated with star tree dimension [%s]", name)

server/src/main/java/org/opensearch/index/compositeindex/datacube/DimensionType.java

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -30,8 +30,14 @@ public enum DimensionType {
3030
DATE,
3131

3232
/**
33-
* Represents a keyword dimension type.
34-
* This is used for dimensions that contain keyword ordinals.
33+
* Represents dimension types which uses ordinals.
34+
* This is used for dimensions that contain sortedSet ordinals.
3535
*/
36-
KEYWORD
36+
ORDINAL,
37+
38+
/**
39+
* Represents an IP dimension type.
40+
* This is used for dimensions that contain IP ordinals.
41+
*/
42+
IP
3743
}
Lines changed: 82 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
/*
2+
* SPDX-License-Identifier: Apache-2.0
3+
*
4+
* The OpenSearch Contributors require contributions made to
5+
* this file be licensed under the Apache-2.0 license or a
6+
* compatible open source license.
7+
*/
8+
9+
package org.opensearch.index.compositeindex.datacube;
10+
11+
import org.apache.lucene.index.DocValuesType;
12+
import org.opensearch.common.annotation.ExperimentalApi;
13+
import org.opensearch.core.xcontent.XContentBuilder;
14+
import org.opensearch.index.mapper.CompositeDataCubeFieldType;
15+
16+
import java.io.IOException;
17+
import java.util.List;
18+
import java.util.Objects;
19+
import java.util.function.Consumer;
20+
21+
/**
22+
* Composite index keyword dimension class
23+
*
24+
* @opensearch.experimental
25+
*/
26+
@ExperimentalApi
27+
public class IpDimension implements Dimension {
28+
public static final String IP = "ip";
29+
private final String field;
30+
31+
public IpDimension(String field) {
32+
this.field = field;
33+
}
34+
35+
@Override
36+
public String getField() {
37+
return field;
38+
}
39+
40+
@Override
41+
public int getNumSubDimensions() {
42+
return 1;
43+
}
44+
45+
@Override
46+
public void setDimensionValues(Long value, Consumer<Long> dimSetter) {
47+
// This will set the keyword dimension value's ordinal
48+
dimSetter.accept(value);
49+
}
50+
51+
@Override
52+
public List<String> getSubDimensionNames() {
53+
return List.of(field);
54+
}
55+
56+
@Override
57+
public DocValuesType getDocValuesType() {
58+
return DocValuesType.SORTED_SET;
59+
}
60+
61+
@Override
62+
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
63+
builder.startObject();
64+
builder.field(CompositeDataCubeFieldType.NAME, field);
65+
builder.field(CompositeDataCubeFieldType.TYPE, IP);
66+
builder.endObject();
67+
return builder;
68+
}
69+
70+
@Override
71+
public boolean equals(Object o) {
72+
if (this == o) return true;
73+
if (o == null || getClass() != o.getClass()) return false;
74+
IpDimension dimension = (IpDimension) o;
75+
return Objects.equals(field, dimension.getField());
76+
}
77+
78+
@Override
79+
public int hashCode() {
80+
return Objects.hash(field);
81+
}
82+
}

server/src/main/java/org/opensearch/index/compositeindex/datacube/KeywordDimension.java renamed to server/src/main/java/org/opensearch/index/compositeindex/datacube/OrdinalDimension.java

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -24,11 +24,11 @@
2424
* @opensearch.experimental
2525
*/
2626
@ExperimentalApi
27-
public class KeywordDimension implements Dimension {
28-
public static final String KEYWORD = "keyword";
27+
public class OrdinalDimension implements Dimension {
28+
public static final String ORDINAL = "ordinal";
2929
private final String field;
3030

31-
public KeywordDimension(String field) {
31+
public OrdinalDimension(String field) {
3232
this.field = field;
3333
}
3434

@@ -62,7 +62,7 @@ public DocValuesType getDocValuesType() {
6262
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
6363
builder.startObject();
6464
builder.field(CompositeDataCubeFieldType.NAME, field);
65-
builder.field(CompositeDataCubeFieldType.TYPE, KEYWORD);
65+
builder.field(CompositeDataCubeFieldType.TYPE, ORDINAL);
6666
builder.endObject();
6767
return builder;
6868
}
@@ -71,7 +71,7 @@ public XContentBuilder toXContent(XContentBuilder builder, Params params) throws
7171
public boolean equals(Object o) {
7272
if (this == o) return true;
7373
if (o == null || getClass() != o.getClass()) return false;
74-
KeywordDimension dimension = (KeywordDimension) o;
74+
OrdinalDimension dimension = (OrdinalDimension) o;
7575
return Objects.equals(field, dimension.getField());
7676
}
7777

server/src/main/java/org/opensearch/index/mapper/IpFieldMapper.java

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@
5252
import org.opensearch.common.logging.DeprecationLogger;
5353
import org.opensearch.common.network.InetAddresses;
5454
import org.opensearch.common.network.NetworkAddress;
55+
import org.opensearch.index.compositeindex.datacube.DimensionType;
5556
import org.opensearch.index.fielddata.IndexFieldData;
5657
import org.opensearch.index.fielddata.ScriptDocValues;
5758
import org.opensearch.index.fielddata.plain.SortedSetOrdinalsIndexFieldData;
@@ -68,6 +69,7 @@
6869
import java.util.Collections;
6970
import java.util.List;
7071
import java.util.Map;
72+
import java.util.Optional;
7173
import java.util.function.BiFunction;
7274
import java.util.function.Supplier;
7375

@@ -161,6 +163,11 @@ public IpFieldMapper build(BuilderContext context) {
161163
);
162164
}
163165

166+
@Override
167+
public Optional<DimensionType> getSupportedDataCubeDimensionType() {
168+
return Optional.of(DimensionType.IP);
169+
}
170+
164171
}
165172

166173
public static final TypeParser PARSER = new TypeParser((n, c) -> {

server/src/main/java/org/opensearch/index/mapper/KeywordFieldMapper.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -260,7 +260,7 @@ public KeywordFieldMapper build(BuilderContext context) {
260260

261261
@Override
262262
public Optional<DimensionType> getSupportedDataCubeDimensionType() {
263-
return Optional.of(DimensionType.KEYWORD);
263+
return Optional.of(DimensionType.ORDINAL);
264264
}
265265
}
266266

0 commit comments

Comments
 (0)