Commit b2babba4 authored by Niklas Selke's avatar Niklas Selke
Browse files

enabled the description parameter for ecoregions and landcover services

parent d30066e2
Pipeline #97297 passed with stages
in 50 seconds
......@@ -167,6 +167,7 @@ DEFAULT_LAT = 48.869359 # home sweet home
DEFAULT_LON = 9.348595
DEFAULT_YEAR = 2012
DEFAULT_RELATIVE = False
DEFAULT_DESCRIPTION = False
DEFAULT_COUNTRY = 'DE'
# Check only position or circle around position within bounds
DEFAULT_CHECK_IS_CIRCLE_INSIDE = False
......
from .serializers import AggSerializer
from utils.views_commons import CommonView
from utils.views_commons import DescriptionMixin, CommonView
from .apps import EcoregionsConfig as Config
class EcoregionsView(CommonView):
class EcoregionsView(DescriptionMixin, CommonView):
def __init__(self):
......
from .serializers import AggSerializer
from utils.views_commons import YearMixin, CommonView
from utils.views_commons import DescriptionMixin, YearMixin, CommonView
from .apps import LandcoverConfig as Config
class LandcoverView(YearMixin, CommonView):
class LandcoverView(DescriptionMixin, YearMixin, CommonView):
def __init__(self):
......
......@@ -64,6 +64,9 @@ class GeneralAggSerializer(BaseSerializer):
if 'additional_properties' in obj:
for key, val in obj['additional_properties'].items():
properties[key] = val
if key == 'description':
properties['many'] = False
properties[agg_function] = obj[agg_function]
# create response
if 'year' in obj:
......
......@@ -449,9 +449,9 @@ class TestCommonView(TestCase):
def test_init_blank(self):
self.assertListEqual(self.view_blank.DEFAULT_KEYS, ['DEFAULT_AGG', 'DEFAULT_CHECK_IS_CIRCLE_INSIDE',
'DEFAULT_COUNTRY', 'DEFAULT_HIGHWAY_TYPES',
'DEFAULT_LAT', 'DEFAULT_LON', 'DEFAULT_RADIUS',
'DEFAULT_RELATIVE', 'DEFAULT_YEAR'])
'DEFAULT_COUNTRY', 'DEFAULT_DESCRIPTION',
'DEFAULT_HIGHWAY_TYPES', 'DEFAULT_LAT', 'DEFAULT_LON',
'DEFAULT_RADIUS', 'DEFAULT_RELATIVE', 'DEFAULT_YEAR'])
self.assertDictEqual(self.view_blank.STATS, {'mean': np.mean, 'min': np.amin, 'max': np.amax,
'median': np.median, 'percentile': np.percentile, 'sum': np.sum,
'stddev': np.std})
......
......@@ -304,7 +304,7 @@ class BaseView(APIView):
self.provenance = self.geo_cube_connection.get_provenance()
self.provenance['timestamp'] = dt.datetime.now().isoformat()
def _extract(self, lat, lon, radius, agg, direction, check_is_circle_inside=False, year=None, relative=False):
def _extract(self, lat, lon, radius, agg, direction, check_is_circle_inside=False, year=None, relative=False, description=False):
"""perform actual extraction of desired quantity"""
print('**direction:', direction, '** radius, agg = ', radius, agg)
bins = None
......@@ -327,13 +327,21 @@ class BaseView(APIView):
radius=radius, min_angle=min_angle, max_angle=max_angle,
agg=agg_function, global_data=self.global_data,
check_is_circle_inside=check_is_circle_inside, relative=relative)
if not np.isscalar(result_tmp):
if self.bins is None:
bins = list(range(self.min_valid, self.max_valid + 1))
else:
bins = self.bins
if len(result_tmp) > len(bins):
bins.append('nan')
if description:
total = np.sum(result_tmp[1])
result_tmp = ", ".join([
f"{val:.0f}: {100.*count / total:.1f} %"
for val, count in sorted(dict(zip(*result_tmp)).items(), key=lambda x: x[1], reverse=True)
if count / total >= 0.01
])
else:
if not np.isscalar(result_tmp):
if self.bins is None:
bins = list(range(self.min_valid, self.max_valid + 1))
else:
bins = self.bins
if len(result_tmp) > len(bins):
bins.append('nan')
result_list.append(result_tmp)
......@@ -460,6 +468,46 @@ class RelativeMixin:
return rawdata
class DescriptionMixin:
@staticmethod
def get_description_param(params):
"""This is a mandatory parameter"""
val = params.get('description')
# if not found, raise error
if val is None:
if settings.DEBUG:
val = settings.DEFAULT_DESCRIPTION
else:
raise KeyError('description is a mandatory query argument')
if isinstance(val, str):
if val.lower() in ['true', 'yes', 'y']:
val = True
elif val.lower() in ['false', 'no', 'n']:
val = False
else:
raise ValueError('query argument for description (%s) must be true or false' % (val))
return val
def get_query_params(self, params, param_keys=None, add_agg=True):
query_params = super().get_query_params(params)
query_params['description'] = self.get_description_param(params)
if query_params['description']:
query_params['radius'] = 25000.
query_params['agg'] = 'counts'
self.STATS['counts'] = partial(np.unique, return_counts=True)
return query_params
def get_rawdata(self, query_params, direction, bins, agg, result, provenance):
if query_params['description']:
agg = 'value'
query_params['agg'] = None
del self.STATS['counts']
rawdata = super().get_rawdata(query_params, direction, bins, agg, result, provenance)
rawdata['additional_properties'] = {**rawdata.get('additional_properties', {}), **{'description': query_params['description']}}
return rawdata
##### BAUSTELLE!! #######
def usage(lat, lng, stats): # pragma: no cover
"""Display proper usage of REST URL"""
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment