"""
@package   mqtt-device-status-service
@file      mqtt_device_status_service.py
@brief     Publishes device status via MQTT

@author    andy wright
@date      10/06/2024
@copyright Copyright 2024 Hanover Displays Limited.
@license   This program is the confidential and proprietary product of
           Hanover Displays Limited. Any unauthorised use, reproduction or
           transfer of this program is strictly prohibited. (Subject to
           limited distribution and restricted disclosure only.) All
           rights reserved.
"""

import time
import datetime
import argparse
import mqtt_service as mqtt
import logging
import signal
logger = logging.getLogger(__name__)

class deviceStatusService(object):
    def __init__(self, broker            = "127.0.0.1",
                       port              = 1883,
                       user_name         = "",
                       password          = "",
                       deviceID          = "",
                       customerID        = "",
                       VIN               = "",
                ):

        def inc_level(sig, frame):
            level = logger.getEffectiveLevel()
            if level == logging.CRITICAL:
                logger.setLevel(logging.ERROR)
            elif level == logging.ERROR:
                logger.setLevel(logging.WARNING)
            elif level == logging.WARNING:
                logger.setLevel(logging.INFO)
            elif level == logging.INFO:
                logger.setLevel(logging.DEBUG)
            print(f"Set logging to {logging.getLevelName(logger.getEffectiveLevel())}")

        def dec_level(sig, frame):
            level = logger.getEffectiveLevel()
            if level == logging.NOTSET:
                logger.setLevel(logging.DEBUG)
            elif level == logging.DEBUG:
                logger.setLevel(logging.INFO)
            elif level == logging.INFO:
                logger.setLevel(logging.WARNING)
            elif level == logging.WARNING:
                logger.setLevel(logging.ERROR)
            elif level == logging.ERROR:
                logger.setLevel(logging.CRITICAL)
            print(f"Set logging to {logging.getLevelName(logger.getEffectiveLevel())}")

        signal.signal(signal.SIGUSR2, inc_level)
        signal.signal(signal.SIGUSR1, dec_level)


        self.device_status_dictionary = {
            "atDateTime": "",
            "status":     ""
        }

        if deviceID == "":
            self.topic = "status"
        else:
            self.topic = customerID + "/" + VIN + "/hanover/" + deviceID + "/status"

        self.mqttService = mqtt.mqttService("mqtt-device-status-service",
                                            broker    = broker,
                                            port      = port,
                                            user_name = user_name,
                                            password  = password)

    def setPayload(self, status = None):
        if status != None:
            self.device_status_dictionary["status"] = status

    def setStatus(self, status):
            self.device_status_dictionary["status"] = status


    def publish(self):
        self.device_status_dictionary["atDateTime"] = datetime.datetime.now().astimezone().replace(microsecond=0).isoformat()
        logger.debug(f"publish - {self.topic}\n{self.device_status_dictionary}\n")
        self.mqttService.publish(self.topic, self.device_status_dictionary)

if __name__ == "__main__":
    # Instantiate the parser
    parser = argparse.ArgumentParser(description='Publishes device status via MQTT')

    # Parse arguments
    parser.add_argument('--period', type=int, default=5, help='MQTT message publish period in seconds (default 5 seconds)')
    parser.add_argument('--status', type=str, default="OK", help='Device status to publish (default "OK")')
    args = parser.parse_args()

    #use local broker to forward topics
    deviceStatusService = deviceStatusService()

    #send topics direct to cloud
    #deviceStatusService = deviceStatusService(broker            = "mqtt.ver.hanover.cloud",
    #                                          port              = 2023,
    #                                          user_name         = "1031_300",
    #                                          password          = "z3Qs38jn",
    #                                          deviceID          = "EG4",
    #                                          customerID        = "1031",
    #                                          VIN               = "0")

    deviceStatusService.setPayload(status = args.status)

    while 1:
        deviceStatusService.publish()
        time.sleep(args.period)
