2021-03-14 11:52:46 +01:00
# -*- coding: utf-8 -*-
import asyncio
2023-01-22 19:53:54 +01:00
from cbpi . api . dataclasses import NotificationAction , NotificationType
2021-03-18 19:27:03 +01:00
from cbpi . api import parameters , Property , CBPiSensor
2021-11-22 17:33:46 +01:00
from cbpi . api import *
import logging
import json
2023-01-22 19:53:54 +01:00
import time
2023-01-23 07:15:29 +01:00
from datetime import datetime
2021-03-14 11:52:46 +01:00
2021-11-22 17:33:46 +01:00
@parameters ( [ Property . Text ( label = " Topic " , configurable = True , description = " MQTT Topic " ) ,
Property . Text ( label = " PayloadDictionary " , configurable = True , default_value = " " ,
2023-01-22 19:53:54 +01:00
description = " Where to find msg in payload, leave blank for raw payload " ) ,
Property . Number ( label = " Timeout " , configurable = " True " , unit = " sec " ,
description = " Timeout in seconds to send notification (default:60 | deactivated: 0) " ) ] )
2021-03-14 11:52:46 +01:00
class MQTTSensor ( CBPiSensor ) :
2021-03-18 19:27:03 +01:00
2021-03-14 11:52:46 +01:00
def __init__ ( self , cbpi , id , props ) :
super ( MQTTSensor , self ) . __init__ ( cbpi , id , props )
2021-11-22 17:33:46 +01:00
self . Topic = self . props . get ( " Topic " , None )
self . payload_text = self . props . get ( " PayloadDictionary " , None )
if self . payload_text != None :
self . payload_text = self . payload_text . split ( ' . ' )
self . mqtt_task = self . cbpi . satellite . subcribe ( self . Topic , self . on_message )
2022-03-07 15:03:41 +01:00
self . value : float = 999
2023-01-22 19:53:54 +01:00
self . timeout = int ( self . props . get ( " Timeout " , 60 ) )
self . starttime = time . time ( )
self . notificationsend = False
self . nextchecktime = self . starttime + self . timeout
2023-01-23 07:15:29 +01:00
self . lastdata = time . time ( )
self . sensor = self . get_sensor ( self . id )
2023-01-22 19:53:54 +01:00
async def Confirm ( self , * * kwargs ) :
self . nextchecktime = time . time ( ) + self . timeout
self . notificationsend = False
pass
async def message ( self ) :
2023-01-23 07:15:29 +01:00
target_timestring = datetime . fromtimestamp ( self . lastdata )
self . cbpi . notify ( " MQTTSensor Timeout " , " Sensor ' " + str ( self . sensor . name ) + " ' did not respond. Last data received: " + target_timestring . strftime ( " % D % H: % M " ) , NotificationType . WARNING , action = [ NotificationAction ( " OK " , self . Confirm ) ] )
2023-01-22 19:53:54 +01:00
pass
2021-03-18 19:27:03 +01:00
2021-11-22 17:33:46 +01:00
async def on_message ( self , message ) :
val = json . loads ( message )
try :
if self . payload_text is not None :
for key in self . payload_text :
val = val . get ( key , None )
if isinstance ( val , ( int , float , str ) ) :
self . value = float ( val )
self . log_data ( self . value )
self . push_update ( self . value )
2023-01-22 19:53:54 +01:00
if self . timeout != 0 :
self . nextchecktime = time . time ( ) + self . timeout
self . notificationsend = False
2023-01-23 07:15:29 +01:00
self . lastdata = time . time ( )
2021-11-22 17:33:46 +01:00
except Exception as e :
logging . info ( " MQTT Sensor Error {} " . format ( e ) )
2021-03-14 11:52:46 +01:00
async def run ( self ) :
2021-03-18 19:27:03 +01:00
while self . running :
2023-01-22 19:53:54 +01:00
if self . timeout != 0 :
if time . time ( ) > self . nextchecktime and self . notificationsend == False :
await self . message ( )
self . notificationsend = True
2021-03-14 11:52:46 +01:00
await asyncio . sleep ( 1 )
def get_state ( self ) :
return dict ( value = self . value )
async def on_stop ( self ) :
if self . mqtt_task . done ( ) is False :
self . mqtt_task . cancel ( )
try :
await self . mqtt_task
except asyncio . CancelledError :
pass
2021-03-18 19:27:03 +01:00
def setup ( cbpi ) :
2021-03-14 11:52:46 +01:00
'''
2021-03-18 19:27:03 +01:00
This method is called by the server during startup
2021-03-14 11:52:46 +01:00
Here you need to register your plugins at the server
2021-03-18 19:27:03 +01:00
: param cbpi : the cbpi core
: return :
2021-03-14 11:52:46 +01:00
'''
2021-11-23 17:33:58 +01:00
if str ( cbpi . static_config . get ( " mqtt " , False ) ) . lower ( ) == " true " :
2021-03-14 11:52:46 +01:00
cbpi . plugin . register ( " MQTTSensor " , MQTTSensor )