Skip to content

Commit 83b251b

Browse files
zeliestZélie StalhandskeZélie StalhandskeZélie Stalhandskeemanuel-schmid
authored
Feature/api wrapper functions (#289)
* Write api wrapper functions * Add use of wrapper functions to api tutorial * add comments * Update notebook * Continue to develop wrapper functions * fix get_litpop_default for global data * Run api notebook with updated data * Check that only possible properties combinations are suggested * Add possibility to provide country code in wrapper functions * test for api wrapper functions * Allow properties input as parameters in api wrapper functions * get_h/e: omit interactions * get_datasets: outline multi selection * add tests for recent staticmethods involved in get_datasets' `properties` argument handling * some bugfixing and errorhandling * get_litpop_default: via get_exposures clean up obsolete methods * introduce a check for multi_selection properties move supported types to config * get_exposures and get_hazard: introduce a default download limitation on matching datasets in order not to inadvertently flood the disk * Wrapper functions: some changes in the logic of object concatenation. - List forbidden multi selection properties rather than allowed ones - Test for unique e.g., rcp also when rcp is not an argument. - Test for multple versions of the same dataset. * add a convenience function for datasets inspection via DataFrame * fine tuning * adapt tests Co-authored-by: Zélie Stalhandske <[email protected]> Co-authored-by: Zélie Stalhandske <[email protected]> Co-authored-by: Zélie Stalhandske <[email protected]> Co-authored-by: emanuel-schmid <[email protected]>
1 parent de26613 commit 83b251b

File tree

4 files changed

+891
-509
lines changed

4 files changed

+891
-509
lines changed

climada/conf/climada.conf

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,9 @@
5858
"data_api": {
5959
"host": "https://climada.ethz.ch",
6060
"chunk_size": 8192,
61-
"cache_db": "{local_data.system}/.downloads.db"
61+
"cache_db": "{local_data.system}/.downloads.db",
62+
"supported_hazard_types": ["river_flood", "tropical_cyclone", "storm_europe"],
63+
"supported_exposures_types": ["litpop", "crop_production"],
64+
"mutual_properties": ["resolution", "rcp"]
6265
}
6366
}

climada/test/test_api_client.py

Lines changed: 100 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,8 @@
2222
import unittest
2323
from shutil import rmtree
2424

25+
import numpy as np
26+
2527
from climada import CONFIG
2628
from climada.util.api_client import Client, Download
2729

@@ -100,6 +102,104 @@ def test_download_dataset(self):
100102
download.unlink()
101103
rm_empty_dir(download.parent.parent.parent)
102104

105+
def test_get_exposures(self):
106+
client = Client()
107+
exposures = client.get_exposures(exposures_type='litpop',
108+
properties={'country_iso3alpha': ['CHE', 'AUT'],
109+
'fin_mode': 'pop', 'exponents': '(0,1)'},
110+
dump_dir=DATA_DIR)
111+
self.assertEqual(len(exposures.gdf), 8583)
112+
self.assertEqual(np.min(exposures.gdf.region_id), 40)
113+
self.assertEqual(np.max(exposures.gdf.region_id), 756)
114+
self.assertTrue('[0, 1]' in exposures.tag.description)
115+
self.assertTrue('pop' in exposures.tag.description)
116+
exposures
117+
118+
def test_get_exposures_fails(self):
119+
client = Client()
120+
with self.assertRaises(ValueError) as cm:
121+
client.get_exposures(exposures_type='river_flood',
122+
properties={'country_iso3alpha': ['CHE', 'AUT'],
123+
'fin_mode': 'pop', 'exponents': '(0,1)'},
124+
dump_dir=DATA_DIR)
125+
self.assertIn('Valid exposures types are a subset of CLIMADA exposures types. Currently',
126+
str(cm.exception))
127+
128+
with self.assertRaises(ValueError) as cm:
129+
client.get_exposures(exposures_type='litpop',
130+
properties={'fin_mode': 'pop', 'exponents': '(0,1)'},
131+
dump_dir=DATA_DIR)
132+
self.assertIn(' datasets matching the query and the limit is set to 10. You can force ',
133+
str(cm.exception))
134+
135+
def test_get_hazard(self):
136+
client = Client()
137+
hazard = client.get_hazard(hazard_type='river_flood',
138+
properties={'country_name': ['Switzerland', 'Austria'],
139+
'year_range': '2010_2030', 'rcp': 'rcp26'},
140+
dump_dir=DATA_DIR)
141+
self.assertEqual(np.shape(hazard.intensity), (960, 8601))
142+
self.assertEqual(np.min(hazard.centroids.region_id), 40)
143+
self.assertEqual(np.max(hazard.centroids.region_id), 756)
144+
self.assertEqual(np.unique(hazard.date).size, 20)
145+
self.assertEqual(hazard.tag.haz_type, 'RF')
146+
hazard
147+
148+
def test_get_hazard_fails(self):
149+
client = Client()
150+
with self.assertRaises(ValueError) as cm:
151+
client.get_hazard(hazard_type='litpop',
152+
properties={'country_name': ['Switzerland', 'Austria'],
153+
'year_range': '2010_2030', 'rcp': 'rcp26'},
154+
dump_dir=DATA_DIR)
155+
self.assertIn('Valid hazard types are a subset of CLIMADA hazard types. Currently',
156+
str(cm.exception))
157+
158+
with self.assertRaises(ValueError) as cm:
159+
client.get_hazard(hazard_type='river_flood',
160+
properties={'country_name': ['Switzerland', 'Austria'],
161+
'year_range': '2010_2030', 'rcp': ['rcp26', 'rcp85']},
162+
dump_dir=DATA_DIR)
163+
self.assertEqual("Cannot combine datasets, there are distinct values for these properties"
164+
" in your selection: ['rcp']",
165+
str(cm.exception))
166+
167+
def test_get_litpop_default(self):
168+
client = Client()
169+
litpop = client.get_litpop_default(country='LUX', dump_dir=DATA_DIR)
170+
self.assertEqual(len(litpop.gdf), 188)
171+
self.assertEqual(np.unique(litpop.gdf.region_id), 442)
172+
self.assertTrue('[1, 1]' in litpop.tag.description)
173+
self.assertTrue('pc' in litpop.tag.description)
174+
175+
def test_multi_filter(self):
176+
client = Client()
177+
testds = client.get_datasets(data_type='storm_europe')
178+
179+
# assert no systemic loss in filtering
180+
still = client._filter_datasets(testds, dict())
181+
for o, r in zip(testds, still):
182+
self.assertEqual(o, r)
183+
184+
# assert filter is effective
185+
p = 'country_name'
186+
a, b = 'Germany', 'Netherlands'
187+
less = client._filter_datasets(testds, {p:[a, b]})
188+
self.assertLess(len(less), len(testds))
189+
only = client._filter_datasets(testds, {p:[a]})
190+
self.assertLess(len(only), len(less))
191+
self.assertLess(0, len(only))
192+
193+
def test_multiplicity_split(self):
194+
properties = {
195+
'country_name': ['x', 'y', 'z'],
196+
'b': '1'
197+
}
198+
# assert split matches expectations
199+
straight, multi = Client._divide_straight_from_multi(properties)
200+
self.assertEqual(straight, {'b': '1'})
201+
self.assertEqual(multi, {'country_name': ['x', 'y', 'z']})
202+
103203

104204
def rm_empty_dir(folder):
105205
for subfolder in folder.iterdir():

0 commit comments

Comments
 (0)