Skip to content

Commit

Permalink
Add geo shape filter field to supported filter formats (#3605)
Browse files Browse the repository at this point in the history
Add new filter query, 'geo_shape' to search geospatial
field types . This new filter query will replace geo_polygon
query later. With this fiter, dashboard can perform spatial
relationssips with shape or predefined shape from an index
against an index.

Signed-off-by: Vijayan Balasubramanian <balasvij@amazon.com>
(cherry picked from commit 71eb3f2)
Signed-off-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>

# Conflicts:
#	CHANGELOG.md
  • Loading branch information
github-actions[bot] committed Mar 23, 2023
1 parent 4339f42 commit aec18b8
Show file tree
Hide file tree
Showing 5 changed files with 126 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
/*
* Copyright OpenSearch Contributors
* SPDX-License-Identifier: Apache-2.0
*/

import { GeoShapeFilter, getGeoShapeFilterField, Polygon, ShapeFilter } from './geo_shape_filter';
import { GeoShapeRelation } from '@opensearch-project/opensearch/api/types';

describe('geo shape filter', function () {
describe('getGeoShapeFilterField', function () {
it('should return the name of the field a geo_shape query is targeting', () => {
const polygon: Polygon = {
coordinates: [
[
[74.006, 40.7128],
[71.0589, 42.3601],
[73.7562, 42.6526],
[74.006, 40.7128],
],
[
[72.6734, 41.7658],
[72.6506, 41.5623],
[73.0515, 41.5582],
[72.6734, 41.7658],
],
],
type: 'Polygon',
};
const geoShapeQuery: {
shape: ShapeFilter;
relation: GeoShapeRelation;
} = {
shape: polygon,
relation: 'intersects',
};
const filter: GeoShapeFilter = {
geo_shape: {
geoPointField: geoShapeQuery,
ignore_unmapped: true,
},
meta: {
disabled: false,
negate: false,
alias: null,
params: geoShapeQuery,
},
};
const result = getGeoShapeFilterField(filter);
expect(result).toBe('geoPointField');
});
it('should return undefined if filter.geo_shape is undefined', () => {
const filter: GeoShapeFilter = {
geo_shape: undefined,
meta: {
disabled: false,
negate: false,
alias: null,
params: {
shape: undefined,
},
},
};
const result = getGeoShapeFilterField(filter);
expect(result).toBeUndefined();
});
});
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
/*
* Copyright OpenSearch Contributors
* SPDX-License-Identifier: Apache-2.0
*/

import { GeoShapeRelation } from '@opensearch-project/opensearch/api/types';
import { Filter, FilterMeta } from './meta_filter';

export type Position = number[];

export interface PreIndexedShapeFilter {
index: string;
id: string;
path: string;
routing?: string;
}

export interface Polygon {
type: 'Polygon';
coordinates: Position[][];
}

export interface MultiPolygon {
type: 'MultiPolygon';
coordinates: Position[][][];
}

// TODO: support other geometries too.
export type ShapeFilter = Polygon | MultiPolygon;

export type GeoShapeFilterMeta = FilterMeta & {
params: {
shape?: ShapeFilter;
indexed_shape?: PreIndexedShapeFilter;
relation?: GeoShapeRelation;
};
};

export type GeoShapeFilter = Filter & {
meta: GeoShapeFilterMeta;
geo_shape: any;
};

export const isGeoShapeFilter = (filter: any): filter is GeoShapeFilter => filter?.geo_shape;

export const getGeoShapeFilterField = (filter: GeoShapeFilter): string | undefined => {
if (filter?.geo_shape === undefined) {
return undefined;
}
return (
filter?.geo_shape && Object.keys(filter.geo_shape).find((key) => key !== 'ignore_unmapped')
);
};
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ import { getPhraseFilterField, isPhraseFilter } from './phrase_filter';
import { getPhrasesFilterField, isPhrasesFilter } from './phrases_filter';
import { getRangeFilterField, isRangeFilter } from './range_filter';
import { getMissingFilterField, isMissingFilter } from './missing_filter';
import { getGeoShapeFilterField, isGeoShapeFilter } from './geo_shape_filter';

export const getFilterField = (filter: Filter) => {
if (isExistsFilter(filter)) {
Expand All @@ -59,6 +60,9 @@ export const getFilterField = (filter: Filter) => {
if (isMissingFilter(filter)) {
return getMissingFilterField(filter);
}
if (isGeoShapeFilter(filter)) {
return getGeoShapeFilterField(filter);
}

return;
};
1 change: 1 addition & 0 deletions src/plugins/data/common/opensearch_query/filters/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ export * from './build_filters';
export * from './custom_filter';
export * from './exists_filter';
export * from './geo_bounding_box_filter';
export * from './geo_shape_filter';
export * from './geo_polygon_filter';
export * from './get_display_value';
export * from './get_filter_field';
Expand Down
1 change: 1 addition & 0 deletions src/plugins/data/common/opensearch_query/filters/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -59,5 +59,6 @@ export enum FILTERS {
RANGE = 'range',
GEO_BOUNDING_BOX = 'geo_bounding_box',
GEO_POLYGON = 'geo_polygon',
GEO_SHAPE = 'geo_shape',
SPATIAL_FILTER = 'spatial_filter',
}

0 comments on commit aec18b8

Please sign in to comment.