Partial implementation of the new iot sensors, this change broke the sensor factories and a few unit tests that will be fixed in next commit.

This commit is contained in:
Guille Gutierrez 2022-02-21 13:26:14 -05:00
parent 99f2dea55f
commit 651151c6ac
11 changed files with 152 additions and 185 deletions

View File

@ -52,6 +52,7 @@ class City:
self._city_objects = None self._city_objects = None
self._energy_systems = None self._energy_systems = None
self._fuels = None self._fuels = None
self._stations = []
@property @property
def fuels(self) -> [Fuel]: def fuels(self) -> [Fuel]:
@ -349,11 +350,19 @@ class City:
@property @property
def energy_systems(self) -> Union[List[EnergySystem], None]: def energy_systems(self) -> Union[List[EnergySystem], None]:
""" """
Get energy systems belonging to the city Get energy systems belonging to the city
:return: None or [EnergySystem] :return: None or [EnergySystem]
""" """
return self._energy_systems return self._energy_systems
@property
def stations(self) -> [Station]:
"""
Get the sensors stations belonging to the city
:return: [Station]
"""
return self._stations
@property @property
def city_objects_clusters(self) -> Union[List[CityObjectsCluster], None]: def city_objects_clusters(self) -> Union[List[CityObjectsCluster], None]:
""" """

View File

@ -1,45 +0,0 @@
"""
Energy Sensor module
SPDX - License - Identifier: LGPL - 3.0 - or -later
Copyright © 2020 Project Author Guille Gutierrez guillermo.gutierrezmorote@concordia.ca
"""
import pandas as pd
from city_model_structure.iot.sensor import Sensor
class ConcordiaEnergySensor(Sensor):
"""
Concordia energy sensor.
"""
def __init__(self, name):
super().__init__()
self._name = name
self._interval = 5
self._interval_units = 'minutes'
self._type = 'ConcordiaEnergySensor'
self._units = 'kW'
self._measures = pd.DataFrame(columns=["Date time", "Energy consumption"])
@property
def measures(self) -> pd.DataFrame:
"""
Get sensor measures [yyyy-mm-dd, hh:mm:ss kW]
:return: DataFrame["Date time", "Energy consumption"]
"""
return self._measures
@measures.deleter
def measures(self):
"""
Delete sensor measures
"""
self._measures.drop = None
def add_period(self, measures):
"""
Add or update a period measures to the dataframe
"""
measures = self._measures.append(measures, ignore_index=True)
self._measures = measures.drop_duplicates('Date time', keep='last')

View File

@ -1,45 +0,0 @@
"""
Gas Flow Sensor module
SPDX - License - Identifier: LGPL - 3.0 - or -later
Copyright © 2020 Project Author Pilar Monsalvete Alvarez de Uribarri pilar.monsalvete@concordia.ca
"""
import pandas as pd
from city_model_structure.iot.sensor import Sensor
class ConcordiaGasFlowSensor(Sensor):
"""
Concordia gas flow sensor.
"""
def __init__(self, name):
super().__init__()
self._name = name
self._interval = 5
self._interval_units = 'minutes'
self._type = 'ConcordiaGasFlowSensor'
self._units = 'm3'
self._measures = pd.DataFrame(columns=["Date time", "Gas Flow Cumulative Monthly"])
@property
def measures(self) -> pd.DataFrame:
"""
Get sensor measures [yyyy-mm-dd, hh:mm:ss m3]
:return: DataFrame["Date time", "Gas Flow Cumulative Monthly"]
"""
return self._measures
@measures.deleter
def measures(self):
"""
Delete sensor measures
"""
self._measures.drop = None
def add_period(self, measures):
"""
Add or update a period measures to the dataframe
"""
measures = self._measures.append(measures, ignore_index=True)
self._measures = measures.drop_duplicates('Date time', keep='last')

View File

@ -1,45 +0,0 @@
"""
Temperature Sensor module
SPDX - License - Identifier: LGPL - 3.0 - or -later
Copyright © 2020 Project Author Pilar Monsalvete Alvarez de Uribarri pilar.monsalvete@concordia.ca
"""
import pandas as pd
from city_model_structure.iot.sensor import Sensor
class ConcordiaTemperatureSensor(Sensor):
"""
Concordia temperature sensor.
"""
def __init__(self, name):
super().__init__()
self._name = name
self._interval = 5
self._interval_units = 'minutes'
self._type = 'ConcordiaTemperatureSensor'
self._units = 'Celsius'
self._measures = pd.DataFrame(columns=["Date time", "Temperature"])
@property
def measures(self) -> pd.DataFrame:
"""
Get sensor measures [yyyy-mm-dd, hh:mm:ss Celsius]
:return: DataFrame["Date time", "Temperature"]
"""
return self._measures
@measures.deleter
def measures(self):
"""
Delete sensor measures
"""
self._measures.drop = None
def add_period(self, measures):
"""
Add or update a period measures to the dataframe
"""
measures = self._measures.append(measures, ignore_index=True)
self._measures = measures.drop_duplicates('Date time', keep='last')

View File

@ -1,76 +1,73 @@
""" """
Sensor module Sensor module
SPDX - License - Identifier: LGPL - 3.0 - or -later SPDX - License - Identifier: LGPL - 3.0 - or -later
Copyright © 2020 Project Author Guille Gutierrez guillermo.gutierrezmorote@concordia.ca Copyright © 2022 Project Author Guille Gutierrez guillermo.gutierrezmorote@concordia.ca
""" """
import uuid
from helpers.location import Location from city_model_structure.iot.sensor_measure import SensorMeasure
from city_model_structure.iot.sensor_type import SensorType
class Sensor: class Sensor:
""" """
Sensor abstract class Sensor abstract class
""" """
def __init__(self): def __init__(self, sensor_id=None, model=None, sensor_type=None, indoor=False, board=None):
self._name = None self._id = sensor_id
self._type = None self._model = model
self._units = None self._type = sensor_type
self._location = None self._indoor = indoor
self._board = board
self._measures = []
@property @property
def name(self): def id(self):
""" """
Get sensor name Get the sensor id a random uuid will be assigned if no ID was provided to the constructor
:return: str :return: Id
""" """
if self._name is None: if self._id is None:
raise ValueError('Undefined sensor name') self._id = uuid.uuid4()
return self._name return self._id
@name.setter
def name(self, value):
"""
Set sensor name
:param value: str
"""
if value is not None:
self._name = str(value)
@property @property
def type(self): def type(self) -> SensorType:
""" """
Get sensor type Get sensor type
:return: str :return: SensorTypeEnum or Error
""" """
if self._type is None:
raise ValueError('Unknown sensor type')
return self._type return self._type
@property @property
def units(self): def model(self):
""" """
Get sensor units Get sensor model is any
:return: str :return: str or None
""" """
return self._units return self._model
@property @property
def location(self) -> Location: def board(self):
""" """
Get sensor location Get sensor board if any
:return: Location :return: str or None
""" """
return self._location return self._model
@location.setter
def location(self, value):
"""
Set sensor location
:param value: Location
"""
self._location = value
@property @property
def measures(self): def indoor(self):
"""
Get is the sensor it's located indoor or outdoor
:return: boolean
"""
return self._indoor
@property
def measures(self) -> [SensorMeasure]:
""" """
Raises not implemented error Raises not implemented error
""" """
raise NotImplementedError return self._measures

View File

@ -0,0 +1,40 @@
"""
Sensor measure module
SPDX - License - Identifier: LGPL - 3.0 - or -later
Copyright © 2022 Project Author Guille Gutierrez guillermo.gutierrezmorote@concordia.ca
"""
class SensorMeasure:
def __init__(self, latitude, longitude, utc_timestamp, value):
self._latitude = latitude
self._longitude = longitude
self._utc_timestamp = utc_timestamp
self._value = value
@property
def latitude(self):
"""
Get measure latitude
"""
return self._latitude
@property
def longitude(self):
"""
Get measure longitude
"""
return self._longitude
@property
def utc_timestamp(self):
"""
Get measure timestamp in utc
"""
return self._utc_timestamp
@property
def value(self):
"""
Get sensor measure value
"""
return self._value

View File

@ -0,0 +1,20 @@
"""
Sensor type module
SPDX - License - Identifier: LGPL - 3.0 - or -later
Copyright © 2022 Project Author Guille Gutierrez guillermo.gutierrezmorote@concordia.ca
"""
from enum import Enum
class SensorType(Enum):
HUMIDITY = 0
TEMPERATURE = 1
CO2 = 2
NOISE = 3
PRESSURE = 4
DIRECT_RADIATION = 5
DIFFUSE_RADIATION = 6
GLOBAL_RADIATION = 7
AIR_QUALITY = 8
GAS_FLOW = 9
ENERGY = 10

View File

@ -0,0 +1,41 @@
"""
Station
SPDX - License - Identifier: LGPL - 3.0 - or -later
Copyright © 2022 Project Author Guille Gutierrez guillermo.gutierrezmorote@concordia.ca
"""
import uuid
from city_model_structure.iot.sensor import Sensor
class Station:
def __init__(self, station_id=None, _mobile=False):
self._id = station_id
self._mobile = _mobile
self._sensors = []
@property
def id(self):
"""
Get the station id a random uuid will be assigned if no ID was provided to the constructor
:return: Id
"""
if self._id is None:
self._id = uuid.uuid4()
return self._id
@property
def _mobile(self):
"""
Get if the station is mobile or not
:return: bool
"""
return self._mobile
@property
def sensors(self) -> [Sensor]:
"""
Get the sensors belonging to the station
:return: [Sensor]
"""
return self._sensors

View File

@ -93,6 +93,3 @@ HEATING_SET_POINT = 'HtgSetPt'
# todo: are any of these two the receptacle concept?? # todo: are any of these two the receptacle concept??
EQUIPMENT = 'Equipment' EQUIPMENT = 'Equipment'
ACTIVITY = 'Activity' ACTIVITY = 'Activity'
# Geometry
EPSILON = 0.0000001

View File

@ -5,7 +5,6 @@ Copyright © 2021 Project Author Guille Gutierrez guillermo.gutierrezmorote@conc
""" """
import pandas as pd import pandas as pd
from imports.sensors.concordia_file_report import ConcordiaFileReport from imports.sensors.concordia_file_report import ConcordiaFileReport
from city_model_structure.iot.concordia_energy_sensor import ConcordiaEnergySensor
class ConcordiaEnergyConsumption(ConcordiaFileReport): class ConcordiaEnergyConsumption(ConcordiaFileReport):

View File

@ -67,4 +67,3 @@ class TestSchedulesFactory(TestCase):
for usage_zone in building.usage_zones: for usage_zone in building.usage_zones:
for schedule in usage_zone.schedules: for schedule in usage_zone.schedules:
print(schedule) print(schedule)
print(usage_zone.schedules[schedule])