Skip to content

Commit d3fc4b5

Browse files
committed
Src files for GeoTile and GeoHash Aggregations on GeoShape
Signed-off-by: Navneet Verma <navneev@amazon.com>
1 parent 35605c6 commit d3fc4b5

18 files changed

+468
-33
lines changed

modules/geo/src/main/java/org/opensearch/geo/GeoModulePlugin.java

Lines changed: 2 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -39,21 +39,17 @@
3939
import org.opensearch.geo.search.aggregations.bucket.geogrid.GeoTileGrid;
4040
import org.opensearch.geo.search.aggregations.metrics.GeoBounds;
4141
import org.opensearch.geo.search.aggregations.metrics.GeoBoundsAggregationBuilder;
42-
import org.opensearch.geo.search.aggregations.metrics.GeoBoundsGeoShapeAggregator;
4342
import org.opensearch.geo.search.aggregations.metrics.InternalGeoBounds;
4443
import org.opensearch.index.mapper.GeoShapeFieldMapper;
4544
import org.opensearch.index.mapper.Mapper;
4645
import org.opensearch.plugins.MapperPlugin;
4746
import org.opensearch.plugins.Plugin;
4847
import org.opensearch.plugins.SearchPlugin;
4948
import org.opensearch.search.aggregations.bucket.composite.CompositeAggregation;
50-
import org.opensearch.search.aggregations.support.CoreValuesSourceType;
51-
import org.opensearch.search.aggregations.support.ValuesSourceRegistry;
5249

5350
import java.util.Collections;
5451
import java.util.List;
5552
import java.util.Map;
56-
import java.util.function.Consumer;
5753

5854
public class GeoModulePlugin extends Plugin implements MapperPlugin, SearchPlugin {
5955

@@ -63,7 +59,8 @@ public Map<String, Mapper.TypeParser> getMappers() {
6359
}
6460

6561
/**
66-
* Registering {@link GeoBounds} aggregation on GeoPoint field.
62+
* Registering {@link GeoBounds}, {@link GeoHashGrid}, {@link GeoTileGrid} aggregation on GeoPoint and GeoShape
63+
* fields.
6764
*/
6865
@Override
6966
public List<AggregationSpec> getAggregations() {
@@ -105,23 +102,4 @@ public List<CompositeAggregationSpec> getCompositeAggregations() {
105102
)
106103
);
107104
}
108-
109-
/**
110-
* Registering the GeoBounds Aggregation on the GeoShape Field. This function allows plugins to register new
111-
* aggregations using aggregation names that are already defined in Core, as long as the new aggregations target
112-
* different ValuesSourceTypes.
113-
*
114-
* @return A list of the new registrar functions
115-
*/
116-
@Override
117-
public List<Consumer<ValuesSourceRegistry.Builder>> getAggregationExtentions() {
118-
final Consumer<ValuesSourceRegistry.Builder> geoShapeConsumer = builder -> builder.register(
119-
GeoBoundsAggregationBuilder.REGISTRY_KEY,
120-
CoreValuesSourceType.GEO_SHAPE,
121-
GeoBoundsGeoShapeAggregator::new,
122-
true
123-
);
124-
return Collections.singletonList(geoShapeConsumer);
125-
}
126-
127105
}

modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/composite/GeoTileGridValuesSourceBuilder.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -42,7 +42,7 @@
4242
import org.opensearch.common.xcontent.ObjectParser;
4343
import org.opensearch.common.xcontent.XContentBuilder;
4444
import org.opensearch.common.xcontent.XContentParser;
45-
import org.opensearch.geo.search.aggregations.bucket.geogrid.CellIdSource;
45+
import org.opensearch.geo.search.aggregations.bucket.geogrid.cells.CellIdSource;
4646
import org.opensearch.geo.search.aggregations.bucket.geogrid.GeoTileGridAggregationBuilder;
4747
import org.opensearch.index.mapper.MappedFieldType;
4848
import org.opensearch.index.query.QueryShardContext;

modules/geo/src/main/java/org/opensearch/geo/search/aggregations/metrics/GeoGridAggregatorSupplier.java renamed to modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/geogrid/GeoGridAggregatorSupplier.java

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,10 +30,9 @@
3030
* GitHub history for details.
3131
*/
3232

33-
package org.opensearch.geo.search.aggregations.metrics;
33+
package org.opensearch.geo.search.aggregations.bucket.geogrid;
3434

3535
import org.opensearch.common.geo.GeoBoundingBox;
36-
import org.opensearch.geo.search.aggregations.bucket.geogrid.GeoGridAggregator;
3736
import org.opensearch.search.aggregations.Aggregator;
3837
import org.opensearch.search.aggregations.AggregatorFactories;
3938
import org.opensearch.search.aggregations.CardinalityUpperBound;

modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/geogrid/GeoHashGridAggregationBuilder.java

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,6 @@
4040
import org.opensearch.search.aggregations.AggregationBuilder;
4141
import org.opensearch.search.aggregations.AggregatorFactories;
4242
import org.opensearch.search.aggregations.AggregatorFactory;
43-
import org.opensearch.geo.search.aggregations.metrics.GeoGridAggregatorSupplier;
4443
import org.opensearch.search.aggregations.support.ValuesSourceAggregatorFactory;
4544
import org.opensearch.search.aggregations.support.ValuesSourceConfig;
4645
import org.opensearch.search.aggregations.support.ValuesSourceRegistry;

modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/geogrid/GeoHashGridAggregatorFactory.java

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,9 @@
3333
package org.opensearch.geo.search.aggregations.bucket.geogrid;
3434

3535
import org.opensearch.common.geo.GeoBoundingBox;
36+
import org.opensearch.geo.search.aggregations.bucket.geogrid.cells.CellIdSource;
37+
import org.opensearch.geo.search.aggregations.bucket.geogrid.cells.GeoShapeCellIdSource;
38+
import org.opensearch.geo.search.aggregations.bucket.geogrid.util.GeoShapeHashUtil;
3639
import org.opensearch.geometry.utils.Geohash;
3740
import org.opensearch.index.query.QueryShardContext;
3841
import org.opensearch.search.aggregations.Aggregator;
@@ -120,6 +123,7 @@ protected Aggregator doCreateInternal(
120123
}
121124

122125
static void registerAggregators(ValuesSourceRegistry.Builder builder) {
126+
// register GeoPoint Aggregation
123127
builder.register(
124128
GeoHashGridAggregationBuilder.REGISTRY_KEY,
125129
CoreValuesSourceType.GEOPOINT,
@@ -155,5 +159,41 @@ static void registerAggregators(ValuesSourceRegistry.Builder builder) {
155159
},
156160
true
157161
);
162+
// register GeoShape Aggregation
163+
builder.register(
164+
GeoHashGridAggregationBuilder.REGISTRY_KEY,
165+
CoreValuesSourceType.GEO_SHAPE,
166+
(
167+
name,
168+
factories,
169+
valuesSource,
170+
precision,
171+
geoBoundingBox,
172+
requiredSize,
173+
shardSize,
174+
aggregationContext,
175+
parent,
176+
cardinality,
177+
metadata) -> {
178+
final GeoShapeCellIdSource cellIdSource = new GeoShapeCellIdSource(
179+
(ValuesSource.GeoShape) valuesSource,
180+
precision,
181+
geoBoundingBox,
182+
GeoShapeHashUtil::encodeShape
183+
);
184+
return new GeoHashGridAggregator(
185+
name,
186+
factories,
187+
cellIdSource,
188+
requiredSize,
189+
shardSize,
190+
aggregationContext,
191+
parent,
192+
cardinality,
193+
metadata
194+
);
195+
},
196+
true
197+
);
158198
}
159199
}

modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/geogrid/GeoTileGridAggregationBuilder.java

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,6 @@
3939
import org.opensearch.search.aggregations.AggregationBuilder;
4040
import org.opensearch.search.aggregations.AggregatorFactories;
4141
import org.opensearch.search.aggregations.AggregatorFactory;
42-
import org.opensearch.geo.search.aggregations.metrics.GeoGridAggregatorSupplier;
4342
import org.opensearch.search.aggregations.bucket.GeoTileUtils;
4443
import org.opensearch.search.aggregations.support.ValuesSourceAggregatorFactory;
4544
import org.opensearch.search.aggregations.support.ValuesSourceConfig;

modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/geogrid/GeoTileGridAggregatorFactory.java

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,8 @@
3333
package org.opensearch.geo.search.aggregations.bucket.geogrid;
3434

3535
import org.opensearch.common.geo.GeoBoundingBox;
36+
import org.opensearch.geo.search.aggregations.bucket.geogrid.cells.CellIdSource;
37+
import org.opensearch.geo.search.aggregations.bucket.geogrid.cells.GeoShapeCellIdSource;
3638
import org.opensearch.index.query.QueryShardContext;
3739
import org.opensearch.search.aggregations.Aggregator;
3840
import org.opensearch.search.aggregations.AggregatorFactories;
@@ -154,5 +156,42 @@ static void registerAggregators(ValuesSourceRegistry.Builder builder) {
154156
},
155157
true
156158
);
159+
160+
// registers Aggregation on GeoShape
161+
builder.register(
162+
GeoTileGridAggregationBuilder.REGISTRY_KEY,
163+
CoreValuesSourceType.GEO_SHAPE,
164+
(
165+
name,
166+
factories,
167+
valuesSource,
168+
precision,
169+
geoBoundingBox,
170+
requiredSize,
171+
shardSize,
172+
aggregationContext,
173+
parent,
174+
cardinality,
175+
metadata) -> {
176+
GeoShapeCellIdSource cellIdSource = new GeoShapeCellIdSource(
177+
(ValuesSource.GeoShape) valuesSource,
178+
precision,
179+
geoBoundingBox,
180+
GeoTileUtils::encodeShape
181+
);
182+
return new GeoTileGridAggregator(
183+
name,
184+
factories,
185+
cellIdSource,
186+
requiredSize,
187+
shardSize,
188+
aggregationContext,
189+
parent,
190+
cardinality,
191+
metadata
192+
);
193+
},
194+
true
195+
);
157196
}
158197
}

modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/geogrid/BoundedCellValues.java renamed to modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/geogrid/cells/BoundedCellValues.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@
2929
* GitHub history for details.
3030
*/
3131

32-
package org.opensearch.geo.search.aggregations.bucket.geogrid;
32+
package org.opensearch.geo.search.aggregations.bucket.geogrid.cells;
3333

3434
import org.opensearch.common.geo.GeoBoundingBox;
3535
import org.opensearch.index.fielddata.MultiGeoPointValues;

modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/geogrid/CellIdSource.java renamed to modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/geogrid/cells/CellIdSource.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@
2929
* GitHub history for details.
3030
*/
3131

32-
package org.opensearch.geo.search.aggregations.bucket.geogrid;
32+
package org.opensearch.geo.search.aggregations.bucket.geogrid.cells;
3333

3434
import org.apache.lucene.index.LeafReaderContext;
3535
import org.apache.lucene.index.SortedNumericDocValues;

modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/geogrid/CellValues.java renamed to modules/geo/src/main/java/org/opensearch/geo/search/aggregations/bucket/geogrid/cells/CellValues.java

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@
2929
* GitHub history for details.
3030
*/
3131

32-
package org.opensearch.geo.search.aggregations.bucket.geogrid;
32+
package org.opensearch.geo.search.aggregations.bucket.geogrid.cells;
3333

3434
import org.opensearch.index.fielddata.AbstractSortingNumericDocValues;
3535
import org.opensearch.index.fielddata.MultiGeoPointValues;
@@ -54,12 +54,16 @@ protected CellValues(MultiGeoPointValues geoValues, int precision, CellIdSource.
5454
this.encoder = encoder;
5555
}
5656

57+
// we will need a way to clear the values array, as it is storing the states
5758
@Override
5859
public boolean advanceExact(int docId) throws IOException {
5960
if (geoValues.advanceExact(docId)) {
6061
int docValueCount = geoValues.docValueCount();
6162
resize(docValueCount);
6263
int j = 0;
64+
// we will need a way to convert the shape into a set of GeoTiles. Now, rather than iterating over the
65+
// points as in GeoPoints, we need to add the list of tiles which shape is intersecting with like we are
66+
// doing for the points.
6367
for (int i = 0; i < docValueCount; i++) {
6468
j = advanceValue(geoValues.nextValue(), j);
6569
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,99 @@
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.geo.search.aggregations.bucket.geogrid.cells;
10+
11+
import org.apache.lucene.index.LeafReaderContext;
12+
import org.apache.lucene.index.SortedNumericDocValues;
13+
import org.opensearch.common.geo.GeoBoundingBox;
14+
import org.opensearch.common.geo.GeoShapeDocValue;
15+
import org.opensearch.index.fielddata.GeoShapeValue;
16+
import org.opensearch.index.fielddata.SortedBinaryDocValues;
17+
import org.opensearch.index.fielddata.SortedNumericDoubleValues;
18+
import org.opensearch.search.aggregations.support.ValuesSource;
19+
20+
import java.io.IOException;
21+
import java.util.List;
22+
23+
/**
24+
* ValueSource class which converts the {@link GeoShapeValue} to numeric long values for bucketing. This class uses the
25+
* {@link GeoShapeCellIdSource.GeoShapeLongEncoder} to encode the geo_shape to {@link Long} values which can be iterated
26+
* to do the bucket aggregation.
27+
*
28+
* @opensearch.internal
29+
*/
30+
public class GeoShapeCellIdSource extends ValuesSource.Numeric {
31+
32+
private final ValuesSource.GeoShape geoShape;
33+
private final int precision;
34+
private final GeoBoundingBox geoBoundingBox;
35+
private final GeoShapeCellIdSource.GeoShapeLongEncoder encoder;
36+
37+
public GeoShapeCellIdSource(
38+
final ValuesSource.GeoShape geoShape,
39+
final int precision,
40+
final GeoBoundingBox geoBoundingBox,
41+
final GeoShapeCellIdSource.GeoShapeLongEncoder encoder
42+
) {
43+
this.geoShape = geoShape;
44+
this.geoBoundingBox = geoBoundingBox;
45+
this.precision = precision;
46+
this.encoder = encoder;
47+
}
48+
49+
/**
50+
* Get the current {@link SortedBinaryDocValues}.
51+
*
52+
* @param context {@link LeafReaderContext}
53+
*/
54+
@Override
55+
public SortedBinaryDocValues bytesValues(LeafReaderContext context) throws IOException {
56+
throw new UnsupportedOperationException("The bytesValues operation is not supported on GeoShapeCellIdSource");
57+
}
58+
59+
/**
60+
* Whether the underlying data is floating-point or not.
61+
*/
62+
@Override
63+
public boolean isFloatingPoint() {
64+
return false;
65+
}
66+
67+
/**
68+
* Get the current {@link SortedNumericDocValues}.
69+
*
70+
* @param context {@link LeafReaderContext}
71+
*/
72+
@Override
73+
public SortedNumericDocValues longValues(final LeafReaderContext context) {
74+
if (geoBoundingBox.isUnbounded()) {
75+
return new GeoShapeCellValues.UnboundedCellValues(geoShape.getGeoShapeValues(context), precision, encoder);
76+
}
77+
return new GeoShapeCellValues.BoundedCellValues(geoShape.getGeoShapeValues(context), precision, encoder, geoBoundingBox);
78+
}
79+
80+
/**
81+
* Get the current {@link SortedNumericDoubleValues}.
82+
*
83+
* @param context {@link LeafReaderContext}
84+
*/
85+
@Override
86+
public SortedNumericDoubleValues doubleValues(LeafReaderContext context) {
87+
throw new UnsupportedOperationException("The doubleValues operation is not supported on GeoShapeCellIdSource");
88+
}
89+
90+
/**
91+
* Encoder to encode the GeoShapes to the specific long values for the aggregation.
92+
*
93+
* @opensearch.internal
94+
*/
95+
@FunctionalInterface
96+
public interface GeoShapeLongEncoder {
97+
List<Long> encode(final GeoShapeDocValue geoShapeDocValue, final int precision);
98+
}
99+
}

0 commit comments

Comments
 (0)