Compare commits

...

1 Commits

Author SHA1 Message Date
Evgeny Zinoviev
2f1c00bed4 wip 2023-05-22 07:11:21 +03:00
11 changed files with 126 additions and 49 deletions

View File

@ -3,6 +3,17 @@ from datetime import datetime
from typing import Tuple, List
from .clickhouse import ClickhouseDatabase
from ..api.types import TemperatureSensorLocation
from ..temphum import TempHumNodes
migration_tables_map = {
'temp_diana': TempHumNodes.KBN_SH_HALL.hash(),
'temp_street': TempHumNodes.KBN_BH_2FL_STREET.hash(),
'temp_roof': TempHumNodes.KBN_BH_2FL.hash(),
'temp_room': TempHumNodes.KBN_BH_1FL_BEDROOM.hash(),
'temp_spb1': TempHumNodes.SPB_FLAT120_CABINET.hash(),
'temp': TempHumNodes.KBN_BH_1FL_LIVINGROOM.hash()
}
def get_temperature_table(sensor: TemperatureSensorLocation) -> str:
@ -28,6 +39,37 @@ def get_temperature_table(sensor: TemperatureSensorLocation) -> str:
class SensorsDatabase(ClickhouseDatabase):
def __init__(self):
super().__init__('home')
self.db.execute("""
CREATE TABLE IF NOT EXISTS temphum (
NodeID Uint32,
ClientTime DateTime,
ReceivedTime DateTime,
Temperature Int16,
RelativeHumidity UInt16,
SensorType Enum8('Si7021' = 0, 'DHT12' = 1, 'BME280' = 2),
) ENGINE = MergeTree()
PARTITION BY toYYYYMMDD(ReceivedTime)
ORDER BY (NodeID, ReceivedTime);
""")
def migrate(self):
for table_name, node_id in migration_tables_map.items():
if table_name in ('temp_room',):
sensor_type = 'DHT12'
else:
sensor_type = 'Si7021'
self.logger.info(f'starting copying table {table_name}')
self.db.execute(f"""
INSERT INTO temphum (NodeID, ClientTime, ReceivedTime, Temperature, RelativeHumidify, SensorType)
SELECT {node_id}, ClientTime, ReceivedTime, Temperature, RelativeHumidify, '{sensor_type}' FROM {table_name}
""")
self.logger.info(f'finished copying table {table_name}')
def migrate_del_old_tables(self):
for table_name in migration_tables_map.keys():
self.db.execute(f"DROP TABLE {table_name}")
self.logger.info(f'dropped table {table_name}')
def add_temperature(self,
home_id: int,

View File

@ -1,25 +1,8 @@
import paho.mqtt.client as mqtt
import re
from enum import auto
from .payload.temphum import TempHumDataPayload
from .esp import MqttEspBase
from ..util import HashableEnum
class MqttTempHumNodes(HashableEnum):
KBN_SH_HALL = auto()
KBN_SH_BATHROOM = auto()
KBN_SH_LIVINGROOM = auto()
KBN_SH_BEDROOM = auto()
KBN_BH_2FL = auto()
KBN_BH_2FL_STREET = auto()
KBN_BH_1FL_LIVINGROOM = auto()
KBN_BH_1FL_BEDROOM = auto()
KBN_BH_1FL_BATHROOM = auto()
SPB_FLAT120_CABINET = auto()
class MqttTempHum(MqttEspBase):

View File

@ -1,18 +1,38 @@
from .base import SensorType, TempHumSensor
from .si7021 import Si7021
from .dht12 import DHT12
from importlib import import_module
__all__ = [
'SensorType',
'TempHumSensor',
'TempHumNodes',
'create_sensor'
]
def create_sensor(type: SensorType, bus: int) -> TempHumSensor:
if type == SensorType.Si7021:
return Si7021(bus)
elif type == SensorType.DHT12:
return DHT12(bus)
def __import_sensor(name):
if name == 'si7021':
return import_module('.si7021', __name__).Si7021
elif name == 'dht12':
return import_module('.dht12', __name__).DHT12
else:
raise ValueError('unexpected sensor type')
raise ValueError(f'unexpected sensor type: {name}')
def __getattr__(name):
if name == 'create_sensor':
base = import_module('.base', __name__)
def create_sensor(type: base.SensorType, bus: int) -> base.TempHumSensor:
if type == base.SensorType.Si7021:
return __import_sensor('si7021')(bus)
elif type == base.SensorType.DHT12:
return __import_sensor('dht12')(bus)
else:
raise ValueError(f'unexpected sensor type: {type}')
return create_sensor
elif name in ('SensorType', 'TempHumSensor'):
return getattr(import_module('.base', __name__), name)
elif name == 'TempHumNodes':
return import_module('.nodes', __name__).TempHumNodes

View File

@ -0,0 +1,9 @@
from .base import (
SensorType as SensorType,
TempHumSensor as TempHumSensor
)
from .nodes import TempHumNodes as TempHumNodes
def create_sensor(type: SensorType, bus: int) -> TempHumSensor:
pass

23
src/home/temphum/nodes.py Normal file
View File

@ -0,0 +1,23 @@
from ..util import HashableEnum
from enum import auto
class TempHumNodes(HashableEnum):
KBN_SH_HALL = auto()
KBN_SH_BATHROOM = auto()
KBN_SH_LIVINGROOM = auto()
KBN_SH_BEDROOM = auto()
KBN_BH_2FL = auto()
KBN_BH_2FL_STREET = auto()
KBN_BH_1FL_LIVINGROOM = auto()
KBN_BH_1FL_BEDROOM = auto()
KBN_BH_1FL_BATHROOM = auto()
KBN_STR_EL_BOX = auto()
SPB_FLAT120_CABINET = auto()
SPB_FLAT120_LIVINGROOM = auto()
SPB_FLAT120_BEDROOM = auto()
SPB_FLAT120_LVR_BALCONY = auto()
SPB_FLAT120_BDR_BALCONY = auto()
SPB_FLAT120_BATHROOM = auto()

View File

@ -1,14 +1,14 @@
#!/usr/bin/env python3
from home.mqtt.temphum import MqttTempHumNodes
from home.temphum import TempHumNodes
if __name__ == '__main__':
max_name_len = 0
for node in MqttTempHumNodes:
for node in TempHumNodes:
if len(node.name) > max_name_len:
max_name_len = len(node.name)
values = []
for node in MqttTempHumNodes:
for node in TempHumNodes:
hash = node.hash()
if hash in values:
raise ValueError(f'collision detected: {hash}')

View File

@ -0,0 +1,10 @@
[Unit]
Description=temperature and humidity sensor node
After=network-online.target
[Service]
Restart=on-failure
ExecStart=/home/user/homekit/src/temphum_native_node.py --config /etc/temphum_node.toml
[Install]
WantedBy=multi-user.target

View File

@ -0,0 +1,10 @@
[Unit]
Description=temperature and humidity sensor node
After=network-online.target
[Service]
Restart=on-failure
ExecStart=/home/user/homekit/src/temphum_native_node.py --config /etc/temphum-node-%i.toml
[Install]
WantedBy=multi-user.target

View File

@ -1,10 +0,0 @@
[Unit]
Description=temperature and humidity daemon
After=network-online.target
[Service]
Restart=on-failure
ExecStart=/home/user/homekit/src/temphumd.py --config /etc/temphumd.toml
[Install]
WantedBy=multi-user.target

View File

@ -1,10 +0,0 @@
[Unit]
Description=temperature and humidity daemon
After=network-online.target
[Service]
Restart=on-failure
ExecStart=/home/user/homekit/src/temphumd.py --config /etc/temphumd-%i.toml
[Install]
WantedBy=multi-user.target