Skip to content

Commit b46d077

Browse files
committed
Add new <dataset>/keyvals endpoint for querying key-val pairs for dataset
1 parent cf4d6ee commit b46d077

File tree

1 file changed

+44
-0
lines changed

1 file changed

+44
-0
lines changed

src/server.py

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -268,6 +268,11 @@ def output(self, key, obj, **kwargs):
268268
show_parser = reqparse.RequestParser(argument_class=CaseInsensitiveArgument)
269269
show_parser.add_argument('crs')
270270

271+
keyvals_parser = reqparse.RequestParser(argument_class=CaseInsensitiveArgument)
272+
keyvals_parser.add_argument('key')
273+
keyvals_parser.add_argument('value')
274+
keyvals_parser.add_argument('filter')
275+
271276
# attachment
272277
get_attachment_parser = reqparse.RequestParser(argument_class=CaseInsensitiveArgument)
273278
get_attachment_parser.add_argument('file', required=True)
@@ -399,6 +404,45 @@ def get(self, dataset):
399404
api.abort(error_code, result['error'])
400405

401406

407+
@api.route('/<path:dataset>/keyvals')
408+
@api.response(404, 'Dataset or feature not found or permission error')
409+
class KeyValues(Resource):
410+
@api.doc('dataset_keyvals')
411+
@api.param('key', 'Key field name')
412+
@api.param('value', 'Value field name')
413+
@api.param(
414+
'filter', 'JSON serialized filter expression: `[["<name>", "<op>", <value>],"and|or",["<name>","<op>",<value>]]`')
415+
@api.expect(keyvals_parser)
416+
@optional_auth
417+
def get(self, dataset):
418+
app.logger.debug(f"Processing GET (dataset_keyvals) on /{dataset}/keyvals")
419+
translator = Translator(app, request)
420+
args = keyvals_parser.parse_args()
421+
key_field_name = args['key']
422+
value_field_name = args['value']
423+
filterexpr = args['filter']
424+
425+
data_service = data_service_handler()
426+
427+
natsort = lambda s: [int(t) if t.isdigit() else t.lower() for t in re.split(r'(\d+)', s)]
428+
429+
result = data_service.index(
430+
get_identity(), translator, dataset, None, None, filterexpr, None, [key_field_name, value_field_name]
431+
)
432+
ret = []
433+
if 'feature_collection' in result:
434+
entries = {}
435+
for feature in result['feature_collection']['features']:
436+
key = feature["id"] if key_field_name == "id" else feature['properties'][key_field_name]
437+
value = str(feature['properties'][value_field_name]).strip()
438+
entries[key] = value
439+
ret = [{"key": kv[0], "value": kv[1]} for kv in entries.items()]
440+
ret.sort(key=lambda record: natsort(record["value"]))
441+
elif 'error' in result:
442+
app.logger.debug(f"Failed to query relation values for {dataset}:{key_field_name}:{value_field_name}: {result['error']}")
443+
return ret
444+
445+
402446
@api.route('/<path:dataset>/<id>')
403447
@api.response(404, 'Dataset or feature not found or permission error')
404448
@api.param('dataset', 'Dataset ID')

0 commit comments

Comments
 (0)