From 955580d9bc0c6d215829a46a2c4fc7abfe33257b Mon Sep 17 00:00:00 2001
From: Tor-Einar Skog <tor-einar.skog@nibio.no>
Date: Tue, 17 Jan 2023 15:38:37 +0100
Subject: [PATCH] Data classes ready

---
 setup.cfg                                     |  2 +-
 src/vipscore_common/entities.py               | 73 +++++++++++++++++++
 src/vipscore_common/modelconfiguration.py     |  0
 .../{model.py => vips_model.py}               |  8 +-
 4 files changed, 78 insertions(+), 5 deletions(-)
 create mode 100644 src/vipscore_common/entities.py
 create mode 100644 src/vipscore_common/modelconfiguration.py
 rename src/vipscore_common/{model.py => vips_model.py} (96%)

diff --git a/setup.cfg b/setup.cfg
index 9b31fb3..1713efd 100644
--- a/setup.cfg
+++ b/setup.cfg
@@ -16,7 +16,7 @@ classifiers =
 package_dir =
     = src
 packages = find:
-python_requires = >=3.6
+python_requires = >=3.7
 
 [options.packages.find]
 where = src
\ No newline at end of file
diff --git a/src/vipscore_common/entities.py b/src/vipscore_common/entities.py
new file mode 100644
index 0000000..3293f45
--- /dev/null
+++ b/src/vipscore_common/entities.py
@@ -0,0 +1,73 @@
+#!/usr/bin/python3
+
+"""
+Copyright (c) 2023 NIBIO <http://www.nibio.no/>. 
+
+This file is part of VIPSCore-Python-Common.
+VIPSCore-Python-Common is free software: you can redistribute it and/or modify
+it under the terms of the NIBIO Open Source License as published by 
+NIBIO, either version 1 of the License, or (at your option) any
+later version.
+ 
+VIPSCore-Python-Common is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+NIBIO Open Source License for more details.
+
+You should have received a copy of the NIBIO Open Source License
+along with VIPSCore-Python-Common.  If not, see <http://www.nibio.no/licenses/>.
+"""
+
+# 
+# @author Tor-Einar Skog <tor-einar.skog@nibio.no>
+# https://www.pedaldrivenprogramming.com/2020/12/fastapi-fundamentals-pydantic/
+
+from datetime import datetime
+from shapely import geometry
+from pydantic import BaseModel, validator, constr
+
+class Result(BaseModel):
+    """Represents a set of DSS model result values for a given point in space (Point, Polygon, MultiPolygon) and time (Period or immediate) """
+    valid_time_start: datetime # TODO make sure it's always timezone aware
+    valid_time_end: datetime # TODO make sure it's always timezone aware
+    valid_geometry: geometry
+    warning_status: int
+    all_values: dict
+
+    def get_keys(self):
+        return set(self.all_values.keys) if self.all_values is not None else set()
+
+    @validator(["valid_time_start","valid_time_end"])
+    def ensure_timezone(cls, v):
+        if v.tzinfo is None or v.tzinfo.utcoffset(v) is None:
+            raise ValueError("%s must be timezone aware" % v)
+        return v
+
+class ModelConfiguration(BaseModel):
+    """All the input data for the model."""
+    config_parameters: dict
+    model_id: constr(min_length=10, max_length=10)
+
+class WeatherObservation(BaseModel):
+    """Data class for a single weather observatin"""
+    element_measurement_type_id: str
+    log_interval_id: int
+    time_measured: datetime
+    value: float
+
+    # Log interval categories
+    LOG_INTERVAL_ID_1M = 8;
+    LOG_INTERVAL_ID_5M = 9;
+    LOG_INTERVAL_ID_10M = 6;
+    LOG_INTERVAL_ID_15M = 5;
+    LOG_INTERVAL_ID_30M = 4;
+    LOG_INTERVAL_ID_1H = 1;
+    LOG_INTERVAL_ID_3H = 3;
+    LOG_INTERVAL_ID_6H = 7;
+    LOG_INTERVAL_ID_1D = 2;
+
+    @validator("time_measured")
+    def ensure_timezone(cls, v):
+        if v.tzinfo is None or v.tzinfo.utcoffset(v) is None:
+            raise ValueError("%s must be timezone aware" % v)
+        return v
diff --git a/src/vipscore_common/modelconfiguration.py b/src/vipscore_common/modelconfiguration.py
new file mode 100644
index 0000000..e69de29
diff --git a/src/vipscore_common/model.py b/src/vipscore_common/vips_model.py
similarity index 96%
rename from src/vipscore_common/model.py
rename to src/vipscore_common/vips_model.py
index 0b0c964..cff828c 100644
--- a/src/vipscore_common/model.py
+++ b/src/vipscore_common/vips_model.py
@@ -22,9 +22,9 @@ along with VIPSCore-Python-Common.  If not, see <http://www.nibio.no/licenses/>.
 # @author Tor-Einar Skog <tor-einar.skog@nibio.no>
 
 from abc import ABC, abstractmethod
-from typing import List, Dict
+from vipscore_common.entities import Result
 
-class Model(ABC):
+class VIPSModel(ABC):
 
     # Default language is English
     default_language = "en"
@@ -40,7 +40,7 @@ class Model(ABC):
         pass
 
     @abstractmethod
-    def get_result(self) -> List[Result]:
+    def get_result(self) -> list[Result]:
         """Get the results as a list of Result objects (TODO ref)"""
         pass
 
@@ -100,6 +100,6 @@ class Model(ABC):
         pass
 
     @abstractmethod
-    def get_sample_config(self) -> Dict:
+    def get_sample_config(self) -> dict:
         """A sample configuration in JSON format (TODO check relation with Dict)"""
         pass
\ No newline at end of file
-- 
GitLab