flood-adapt 0.3.15__py3-none-any.whl → 1.0.0rc1__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,140 @@
1
+ from enum import Enum
2
+ from typing import Optional
3
+
4
+ from pydantic import BaseModel
5
+
6
+
7
+ class FloodmapType(str, Enum):
8
+ """The accepted input for the variable floodmap in Site."""
9
+
10
+ water_level = "water_level"
11
+ water_depth = "water_depth"
12
+
13
+
14
+ class BenefitsModel(BaseModel):
15
+ """The accepted input for the variable benefits in Site.
16
+
17
+ Attributes
18
+ ----------
19
+ current_year : int
20
+ The current year used in benefits calculations.
21
+ current_projection : str
22
+ The current projection used in benefits calculations.
23
+ baseline_strategy : str
24
+ The baseline strategy used in benefits calculations.
25
+ event_set : str
26
+ The event set used in benefits calculations.
27
+ """
28
+
29
+ current_year: int
30
+ current_projection: str
31
+ baseline_strategy: str
32
+ event_set: str
33
+
34
+
35
+ class EquityModel(BaseModel):
36
+ """
37
+ The accepted input for the variable equity in Site.
38
+
39
+ Attributes
40
+ ----------
41
+ census_data : str
42
+ TODO
43
+ percapitaincome_label : Optional[str], default="PerCapitaIncome"
44
+ TODO
45
+ totalpopulation_label : Optional[str], default="TotalPopulation"
46
+ TODO
47
+ """
48
+
49
+ census_data: str
50
+ percapitaincome_label: Optional[str] = "PerCapitaIncome"
51
+ totalpopulation_label: Optional[str] = "TotalPopulation"
52
+
53
+
54
+ class AggregationModel(BaseModel):
55
+ """The accepted input for the variable aggregation in Site.
56
+
57
+ Attributes
58
+ ----------
59
+ name : str
60
+ TODO
61
+ file : str
62
+ TODO
63
+ field_name : str
64
+ TODO
65
+ equity : Optional[EquityModel], default=None
66
+ TODO
67
+ """
68
+
69
+ name: str
70
+ file: str
71
+ field_name: str
72
+ equity: Optional[EquityModel] = None
73
+
74
+
75
+ class BFEModel(BaseModel):
76
+ """The accepted input for the variable bfe in Site.
77
+
78
+ Attributes
79
+ ----------
80
+ geom : str
81
+ TODO
82
+ table : Optional[str], default=None
83
+ TODO
84
+ field_name : str
85
+ TODO
86
+ """
87
+
88
+ geom: str
89
+ table: Optional[str] = None
90
+ field_name: str
91
+
92
+
93
+ class SVIModel(BaseModel):
94
+ """The accepted input for the variable svi in Site.
95
+
96
+ Attributes
97
+ ----------
98
+ geom : str
99
+ TODO
100
+ field_name : str
101
+ TODO
102
+ """
103
+
104
+ geom: str
105
+ field_name: str
106
+
107
+
108
+ class NoFootprintsModel(BaseModel):
109
+ """
110
+ The configuration on the how to show objects with no footprints.
111
+
112
+ Attributes
113
+ ----------
114
+ shape : Optional[str], default="triangle"
115
+ The shape of the object with no footprints.
116
+ diameter_meters : Optional[float], default=10
117
+ The diameter of the object with no footprints in meters.
118
+ """
119
+
120
+ shape: Optional[str] = "triangle"
121
+ diameter_meters: Optional[float] = 10
122
+
123
+
124
+ class RiskModel(BaseModel):
125
+ """The accepted input for the variable risk in Site.
126
+
127
+ Attributes
128
+ ----------
129
+ return_periods : list[int]
130
+ The return periods for the risk model.
131
+ """
132
+
133
+ return_periods: list = [1, 2, 5, 10, 25, 50, 100]
134
+
135
+
136
+ class DamageType(str, Enum):
137
+ """The accepted input for the variable footprints_dmg_type."""
138
+
139
+ absolute = "absolute"
140
+ relative = "relative"
@@ -1,380 +1,23 @@
1
- import math
2
- from enum import Enum
3
1
  from pathlib import Path
4
- from typing import Optional, Union
2
+ from typing import Optional
5
3
 
6
- import numpy as np
7
- import pandas as pd
8
- from plotly.express import line
9
- from plotly.express.colors import sample_colorscale
10
- from pydantic import AfterValidator, BaseModel, Field, model_validator
4
+ from pydantic import BaseModel, model_validator
11
5
  from tomli import load as load_toml
12
- from typing_extensions import Annotated
13
6
 
7
+ from flood_adapt.config.hazard import (
8
+ Cstype,
9
+ CycloneTrackDatabaseModel,
10
+ DemModel,
11
+ FloodFrequencyModel,
12
+ FloodModel,
13
+ ObsPointModel,
14
+ RiverModel,
15
+ SCSModel,
16
+ SlrScenariosModel,
17
+ WaterlevelReferenceModel,
18
+ )
14
19
  from flood_adapt.objects.forcing import unit_system as us
15
20
  from flood_adapt.objects.forcing.tide_gauge import TideGauge
16
- from flood_adapt.objects.forcing.timeseries import Scstype
17
-
18
-
19
- def ensure_ascii(s: str):
20
- assert s.isascii()
21
- return s
22
-
23
-
24
- AsciiStr = Annotated[str, AfterValidator(ensure_ascii)]
25
-
26
-
27
- class Cstype(str, Enum):
28
- """The accepted input for the variable cstype in Site."""
29
-
30
- projected = "projected"
31
- spherical = "spherical"
32
-
33
-
34
- class SCSModel(BaseModel):
35
- """Class describing the accepted input for the variable scs.
36
-
37
- Includes the file with the non-dimensional SCS rainfall curves in the site folder and the SCS rainfall curve type.
38
-
39
- Attributes
40
- ----------
41
- file : str
42
- The path to the SCS rainfall curves file.
43
- type : Scstype
44
- The type of the SCS rainfall curve.
45
- """
46
-
47
- file: str
48
- type: Scstype
49
-
50
-
51
- class RiverModel(BaseModel):
52
- """Model that describes the accepted input for the variable river in Site.
53
-
54
- Attributes
55
- ----------
56
- name : str
57
- The name of the river.
58
- description : Optional[str], default=None
59
- description of the river.
60
- mean_discharge : us.UnitfulDischarge
61
- The mean discharge of the river.
62
- x_coordinate : float
63
- The x coordinate of the river.
64
- y_coordinate : float
65
- The y coordinate of the river.
66
- """
67
-
68
- name: str
69
- description: Optional[str] = None
70
- mean_discharge: us.UnitfulDischarge
71
- x_coordinate: float
72
- y_coordinate: float
73
-
74
-
75
- class ObsPointModel(BaseModel):
76
- """The accepted input for the variable obs_point in Site.
77
-
78
- obs_points is used to define output locations in the hazard model, which will be plotted in the user interface.
79
-
80
- Attributes
81
- ----------
82
- name : Union[int, AsciiStr]
83
- The name of the observation point.
84
- description : Optional[str], default=""
85
- The description of the observation point.
86
- ID : Optional[int], default=None
87
- The ID of the observation point.
88
- file : Optional[str], default=None
89
- The path to the observation point data file.
90
- """
91
-
92
- name: Union[int, AsciiStr]
93
- description: Optional[str] = ""
94
- ID: Optional[int] = (
95
- None # if the observation station is also a tide gauge, this ID should be the same as for obs_station
96
- )
97
- file: Optional[str] = None # for locally stored data
98
- lat: float
99
- lon: float
100
-
101
-
102
- class FloodFrequencyModel(BaseModel):
103
- """The accepted input for the variable flood_frequency in Site."""
104
-
105
- flooding_threshold: us.UnitfulLength
106
-
107
-
108
- class DemModel(BaseModel):
109
- """The accepted input for the variable dem in Site.
110
-
111
- Attributes
112
- ----------
113
- filename : str
114
- The path to the digital elevation model file.
115
- units : us.UnitTypesLength
116
- The units of the digital elevation model file.
117
- """
118
-
119
- filename: str
120
- units: us.UnitTypesLength
121
-
122
-
123
- class FloodmapType(str, Enum):
124
- """The accepted input for the variable floodmap in Site."""
125
-
126
- water_level = "water_level"
127
- water_depth = "water_depth"
128
-
129
-
130
- class DatumModel(BaseModel):
131
- """
132
- The accepted input for the variable datums in WaterlevelReferenceModel.
133
-
134
- Attributes
135
- ----------
136
- name : str
137
- The name of the vertical reference model.
138
- height : us.UnitfulLength
139
- The height of the vertical reference model relative to the main reference.
140
- """
141
-
142
- name: str
143
- height: us.UnitfulLength
144
-
145
-
146
- class WaterlevelReferenceModel(BaseModel):
147
- """The accepted input for the variable water_level in Site.
148
-
149
- Waterlevels timeseries are calculated from user input, assumed to be relative to the `reference` vertical reference model.
150
-
151
- For plotting in the GUI, the `reference` vertical reference model is used as the main zero-reference, all values are relative to this.
152
- All other vertical reference models are plotted as dashed lines.
153
-
154
- Attributes
155
- ----------
156
- reference : str
157
- The name of the vertical reference model that is used as the main zero-reference.
158
- datums : list[DatumModel]
159
- The vertical reference models that are used to calculate the waterlevels timeseries.
160
- The datums are used to calculate the waterlevels timeseries, which are relative to the `reference` vertical reference model.
161
- """
162
-
163
- reference: str
164
- datums: list[DatumModel] = Field(default_factory=list)
165
-
166
- def get_datum(self, name: str) -> DatumModel:
167
- for datum in self.datums:
168
- if datum.name == name:
169
- return datum
170
- raise ValueError(f"Could not find datum with name {name}")
171
-
172
- @model_validator(mode="after")
173
- def main_reference_should_be_in_datums_and_eq_zero(self):
174
- if self.reference not in [datum.name for datum in self.datums]:
175
- raise ValueError(f"Reference {self.reference} not in {self.datums}")
176
- if not math.isclose(
177
- self.get_datum(self.reference).height.value, 0, abs_tol=1e-6
178
- ):
179
- raise ValueError(f"Reference {self.reference} height is not zero")
180
- return self
181
-
182
- @model_validator(mode="after")
183
- def all_datums_should_have_unique_names(self):
184
- datum_names = [datum.name for datum in self.datums]
185
- if len(set(datum_names)) != len(datum_names):
186
- raise ValueError(f"Duplicate datum names found: {datum_names}")
187
- return self
188
-
189
-
190
- class CycloneTrackDatabaseModel(BaseModel):
191
- """The accepted input for the variable cyclone_track_database in Site.
192
-
193
- Attributes
194
- ----------
195
- file : str
196
- The path to the cyclone track database file.
197
- """
198
-
199
- file: str
200
-
201
-
202
- class SlrScenariosModel(BaseModel):
203
- """The accepted input for the variable slr_scenarios.
204
-
205
- Attributes
206
- ----------
207
- file : str
208
- The path to the sea level rise scenarios file.
209
- relative_to_year : int
210
- The year to which the sea level rise scenarios are relative.
211
- """
212
-
213
- file: str
214
- relative_to_year: int
215
-
216
- def interp_slr(
217
- self,
218
- scenario: str,
219
- year: float,
220
- units: us.UnitTypesLength = us.UnitTypesLength.meters,
221
- ) -> float:
222
- """Interpolate SLR value and reference it to the SLR reference year from the site toml.
223
-
224
- Parameters
225
- ----------
226
- csv_path : Path
227
- Path to the slr.csv file containing the SLR scenarios.
228
- scenario : str
229
- SLR scenario name to use from the column names in self.file
230
- year : float
231
- year to evaluate
232
- units : us.UnitTypesLength, default = us.UnitTypesLength.meters
233
- The units to convert the SLR value to. Default is meters.
234
-
235
- Returns
236
- -------
237
- float
238
- The interpolated sea level rise value in the specified units, relative to the reference year.
239
-
240
- Raises
241
- ------
242
- ValueError
243
- if the reference year is outside of the time range in the slr.csv file
244
- ValueError
245
- if the year to evaluate is outside of the time range in the slr.csv file
246
- """
247
- df = pd.read_csv(self.file)
248
- if year > df["year"].max() or year < df["year"].min():
249
- raise ValueError(
250
- "The selected year is outside the range of the available SLR scenarios"
251
- )
252
-
253
- if (
254
- self.relative_to_year > df["year"].max()
255
- or self.relative_to_year < df["year"].min()
256
- ):
257
- raise ValueError(
258
- f"The reference year {self.relative_to_year} is outside the range of the available SLR scenarios"
259
- )
260
-
261
- slr = np.interp(year, df["year"], df[scenario])
262
- ref_slr = np.interp(self.relative_to_year, df["year"], df[scenario])
263
-
264
- new_slr = us.UnitfulLength(
265
- value=slr - ref_slr,
266
- units=df["units"][0],
267
- )
268
- return np.round(new_slr.convert(units), decimals=2)
269
-
270
- def plot_slr_scenarios(
271
- self,
272
- scenario_names: list[str],
273
- output_loc: Path,
274
- units: us.UnitTypesLength = us.UnitTypesLength.meters,
275
- ) -> str:
276
- """
277
- Plot sea level rise scenarios.
278
-
279
- Returns
280
- -------
281
- html_path : str
282
- The path to the html plot of the sea level rise scenarios.
283
- """
284
- df = pd.read_csv(self.file)
285
-
286
- ncolors = len(df.columns) - 2
287
- if "units" not in df.columns:
288
- raise ValueError(f"Expected column `units` in {self.file}.")
289
-
290
- _units = df["units"].iloc[0]
291
- _units = us.UnitTypesLength(_units)
292
-
293
- if "year" not in df.columns:
294
- raise ValueError(f"Expected column `year` in {self.file}.")
295
-
296
- if (
297
- self.relative_to_year > df["year"].max()
298
- or self.relative_to_year < df["year"].min()
299
- ):
300
- raise ValueError(
301
- f"The reference year {self.relative_to_year} is outside the range of the available SLR scenarios"
302
- )
303
-
304
- for scn in scenario_names:
305
- ref_slr = np.interp(self.relative_to_year, df["year"], df[scn])
306
- df[scn] -= ref_slr
307
-
308
- df = df.drop(columns="units").melt(id_vars=["year"]).reset_index(drop=True)
309
- # convert to units used in GUI
310
- conversion_factor = us.UnitfulLength(value=1.0, units=_units).convert(units)
311
- df.iloc[:, -1] = (conversion_factor * df.iloc[:, -1]).round(decimals=2)
312
-
313
- # rename column names that will be shown in html
314
- df = df.rename(
315
- columns={
316
- "variable": "Scenario",
317
- "value": f"Sea level rise [{units.value}]",
318
- }
319
- )
320
-
321
- colors = sample_colorscale(
322
- "rainbow", [n / (ncolors - 1) for n in range(ncolors)]
323
- )
324
- fig = line(
325
- df,
326
- x="year",
327
- y=f"Sea level rise [{units.value}]",
328
- color="Scenario",
329
- color_discrete_sequence=colors,
330
- )
331
-
332
- # fig.update_traces(marker={"line": {"color": "#000000", "width": 2}})
333
-
334
- fig.update_layout(
335
- autosize=False,
336
- height=100 * 1.2,
337
- width=280 * 1.3,
338
- margin={"r": 0, "l": 0, "b": 0, "t": 0},
339
- font={"size": 10, "color": "black", "family": "Arial"},
340
- title_font={"size": 10, "color": "black", "family": "Arial"},
341
- legend_font={"size": 10, "color": "black", "family": "Arial"},
342
- legend_grouptitlefont={"size": 10, "color": "black", "family": "Arial"},
343
- legend={"entrywidthmode": "fraction", "entrywidth": 0.2},
344
- yaxis_title_font={"size": 10, "color": "black", "family": "Arial"},
345
- xaxis_title=None,
346
- xaxis_range=[self.relative_to_year, df["year"].max()],
347
- legend_title=None,
348
- # paper_bgcolor="#3A3A3A",
349
- # plot_bgcolor="#131313",
350
- )
351
-
352
- # write html to results folder
353
- output_loc.parent.mkdir(parents=True, exist_ok=True)
354
- fig.write_html(output_loc)
355
- return str(output_loc)
356
-
357
-
358
- class FloodModel(BaseModel):
359
- """The accepted input for the variable overland_model and offshore_model in Site.
360
-
361
- Attributes
362
- ----------
363
- name : str
364
- The name of the directory in `static/templates/<directory>` that contains the template model files.
365
- reference : str
366
- The name of the vertical reference model that is used as the reference datum. Should be defined in water_level.datums.
367
- vertical_offset : Optional[us.UnitfulLength], default = None
368
- The vertical offset of the vertical reference model relative to the main reference.
369
- Given that the height of the vertical reference model is often determined by external sources,
370
- this vertical offset can be used to correct systematic over-/underestimation of a vertical reference model.
371
- """
372
-
373
- name: str
374
- reference: str
375
-
376
- # this used to be water_level_offset from events
377
- vertical_offset: Optional[us.UnitfulLength] = None
378
21
 
379
22
 
380
23
  class SfincsConfigModel(BaseModel):
@@ -28,14 +28,8 @@ from shapely import MultiLineString, MultiPolygon, Polygon
28
28
 
29
29
  from flood_adapt.adapter.fiat_adapter import _FIAT_COLUMNS
30
30
  from flood_adapt.config.fiat import (
31
- AggregationModel,
32
- BenefitsModel,
33
- BFEModel,
34
- EquityModel,
35
31
  FiatConfigModel,
36
32
  FiatModel,
37
- RiskModel,
38
- SVIModel,
39
33
  )
40
34
  from flood_adapt.config.gui import (
41
35
  AggregationDmgLayer,
@@ -49,21 +43,31 @@ from flood_adapt.config.gui import (
49
43
  SyntheticTideModel,
50
44
  VisualizationLayers,
51
45
  )
52
- from flood_adapt.config.sfincs import (
46
+ from flood_adapt.config.hazard import (
53
47
  Cstype,
54
48
  CycloneTrackDatabaseModel,
55
49
  DatumModel,
56
50
  DemModel,
57
- FloodmapType,
58
51
  FloodModel,
59
52
  ObsPointModel,
60
53
  RiverModel,
61
54
  SCSModel,
62
- SfincsConfigModel,
63
- SfincsModel,
64
55
  SlrScenariosModel,
65
56
  WaterlevelReferenceModel,
66
57
  )
58
+ from flood_adapt.config.impacts import (
59
+ AggregationModel,
60
+ BenefitsModel,
61
+ BFEModel,
62
+ EquityModel,
63
+ FloodmapType,
64
+ RiskModel,
65
+ SVIModel,
66
+ )
67
+ from flood_adapt.config.sfincs import (
68
+ SfincsConfigModel,
69
+ SfincsModel,
70
+ )
67
71
  from flood_adapt.config.site import (
68
72
  Site,
69
73
  StandardObjectModel,
@@ -11,7 +11,7 @@ import pandas as pd
11
11
  import xarray as xr
12
12
  from geopandas import GeoDataFrame
13
13
 
14
- from flood_adapt.config.sfincs import SlrScenariosModel
14
+ from flood_adapt.config.hazard import SlrScenariosModel
15
15
  from flood_adapt.config.site import Site
16
16
  from flood_adapt.dbs_classes.dbs_benefit import DbsBenefit
17
17
  from flood_adapt.dbs_classes.dbs_event import DbsEvent
@@ -5,7 +5,6 @@ from flood_adapt.objects.events.events import (
5
5
  Event,
6
6
  Mode,
7
7
  Template,
8
- TimeFrame,
9
8
  )
10
9
  from flood_adapt.objects.events.historical import HistoricalEvent
11
10
  from flood_adapt.objects.events.hurricane import HurricaneEvent
@@ -16,6 +15,7 @@ from flood_adapt.objects.forcing.forcing import (
16
15
  IForcing,
17
16
  )
18
17
  from flood_adapt.objects.forcing.forcing_factory import ForcingFactory
18
+ from flood_adapt.objects.forcing.time_frame import TimeFrame
19
19
  from flood_adapt.objects.measures.measure_factory import MeasureFactory
20
20
  from flood_adapt.objects.measures.measures import (
21
21
  Buyout,
@@ -57,7 +57,6 @@ __all__ = [
57
57
  "SyntheticEvent",
58
58
  "HistoricalEvent",
59
59
  "HurricaneEvent",
60
- "TimeFrame",
61
60
  "Mode",
62
61
  "Template",
63
62
  # EventSet
@@ -65,6 +64,7 @@ __all__ = [
65
64
  "SubEventModel",
66
65
  # Forcing
67
66
  "ForcingFactory",
67
+ "TimeFrame",
68
68
  "IForcing",
69
69
  "ForcingType",
70
70
  "ForcingSource",
@@ -8,7 +8,7 @@ from typing import Any, ClassVar, List, Type
8
8
  import tomli
9
9
  from pydantic import BaseModel, field_serializer
10
10
 
11
- from flood_adapt.config.sfincs import RiverModel
11
+ from flood_adapt.config.hazard import RiverModel
12
12
  from flood_adapt.misc.log import FloodAdaptLogging
13
13
 
14
14
 
@@ -1,31 +1,26 @@
1
1
  from datetime import datetime
2
2
  from pathlib import Path
3
- from typing import Optional
4
3
 
5
4
  import cht_meteo
6
5
  import numpy as np
7
6
  import xarray as xr
8
7
  from cht_meteo.dataset import MeteoDataset
9
8
 
10
- from flood_adapt.config.config import Settings
11
- from flood_adapt.config.site import Site
12
9
  from flood_adapt.objects.forcing.time_frame import TimeFrame
13
10
 
14
11
 
15
12
  class MeteoHandler:
16
- def __init__(self, dir: Optional[Path] = None, site: Optional[Site] = None) -> None:
17
- self.dir: Path = dir or Settings().database_path / "static" / "meteo"
13
+ def __init__(self, dir: Path, lat: float, lon: float) -> None:
14
+ self.dir: Path = dir
18
15
  self.dir.mkdir(parents=True, exist_ok=True)
19
- self.site: Site = site or Site.load_file(
20
- Settings().database_path / "static" / "config" / "site.toml"
21
- )
16
+
22
17
  # Create GFS dataset
23
18
  self.dataset = cht_meteo.dataset(
24
19
  name="gfs_anl_0p50",
25
20
  source="gfs_analysis_0p50",
26
21
  path=self.dir,
27
- lon_range=(self.site.lon - 10, self.site.lon + 10),
28
- lat_range=(self.site.lat - 10, self.site.lat + 10),
22
+ lon_range=(lon - 10, lon + 10),
23
+ lat_range=(lat - 10, lat + 10),
29
24
  )
30
25
  # quick fix for sites near the 0 degree longitude -> shift the meteo download area either east or west of the 0 degree longitude
31
26
  # TODO implement a good solution to this in cht_meteo
@@ -185,7 +185,7 @@ class Measure(Object):
185
185
 
186
186
  Parameters
187
187
  ----------
188
- filepath : Path | str | os.PathLike
188
+ file_path : Path | str | os.PathLike
189
189
  Path to the file to load the measure from.
190
190
 
191
191
  Returns
@@ -1,7 +1,7 @@
1
1
  import os
2
2
  from pathlib import Path
3
3
 
4
- from flood_adapt.config.sfincs import FloodmapType
4
+ from flood_adapt.config.impacts import FloodmapType
5
5
  from flood_adapt.misc.database_user import DatabaseUser
6
6
  from flood_adapt.misc.log import FloodAdaptLogging
7
7
  from flood_adapt.objects.events.event_set import EventSet
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.2
2
2
  Name: flood-adapt
3
- Version: 0.3.15
3
+ Version: 1.0.0rc1
4
4
  Summary: A software package support system which can be used to assess the benefits and costs of flood resilience measures
5
5
  Author-email: Gundula Winter <Gundula.Winter@deltares.nl>, Panos Athanasiou <Panos.Athanasiou@deltares.nl>, Frederique de Groen <Frederique.deGroen@deltares.nl>, Tim de Wilde <Tim.deWilde@deltares.nl>, Julian Hofer <Julian.Hofer@deltares.nl>, Daley Adrichem <Daley.Adrichem@deltares.nl>, Luuk Blom <Luuk.Blom@deltares.nl>
6
6
  License: GNU GENERAL PUBLIC LICENSE