Add support for mqtt birth message

This commit is contained in:
zewelor
2017-12-06 10:14:43 +01:00
parent 2295cdc1df
commit b32897f949
5 changed files with 74 additions and 27 deletions
+6
View File
@@ -2,6 +2,12 @@ mqtt:
host: 192.168.1.1 host: 192.168.1.1
username: user username: user
password: password password: password
manager:
topic_subcription:
update_all:
topic: homeassistant/status
payload: online
workers: workers:
thermostat: thermostat:
args: args:
+1 -1
View File
@@ -26,7 +26,7 @@ else:
_LOGGER.debug('Starting') _LOGGER.debug('Starting')
mqtt = MqttClient(settings['mqtt']) mqtt = MqttClient(settings['mqtt'])
WorkersManager.start(mqtt, settings['workers']) WorkersManager().register_workers(settings['manager']).start(mqtt)
running = True running = True
+5
View File
@@ -1,11 +1,15 @@
import paho.mqtt.publish as publish import paho.mqtt.publish as publish
import paho.mqtt.client as mqtt import paho.mqtt.client as mqtt
class MqttClient: class MqttClient:
def __init__(self, config): def __init__(self, config):
self._config = config self._config = config
def publish(self, messages): def publish(self, messages):
if messages is None:
return
publish.multiple(list(map(lambda m: m.as_dict, messages)), publish.multiple(list(map(lambda m: m.as_dict, messages)),
hostname=self.hostname, hostname=self.hostname,
auth={'username': self.username, 'password': self.password}) auth={'username': self.username, 'password': self.password})
@@ -34,6 +38,7 @@ class MqttClient:
mqttc.loop_start() mqttc.loop_start()
class MqttMessage: class MqttMessage:
def __init__(self, topic=None, payload=None): def __init__(self, topic=None, payload=None):
self._topic = topic self._topic = topic
+4
View File
@@ -28,6 +28,8 @@ class ThermostatWorker(BaseWorker):
self._reverse_modes = {v: k for k, v in self._mapped_modes.items()} self._reverse_modes = {v: k for k, v in self._mapped_modes.items()}
def get_mapping(self, mode): def get_mapping(self, mode):
if mode < 0:
return None
return self._mapped_modes[mode] return self._mapped_modes[mode]
def get_reverse_mapping(self, mode): def get_reverse_mapping(self, mode):
@@ -67,6 +69,8 @@ class ThermostatWorker(BaseWorker):
_, device_name, method, _ = topic.split('/') _, device_name, method, _ = topic.split('/')
thermostat = self.devices[device_name] thermostat = self.devices[device_name]
value = value.decode('utf-8')
if method == STATE_AWAY: if method == STATE_AWAY:
method = "mode" method = "mode"
value = ModesMapper.on_off_to_mode(value) value = ModesMapper.on_off_to_mode(value)
+46 -14
View File
@@ -20,38 +20,70 @@ class WorkersManager:
_LOGGER.debug(messages) _LOGGER.debug(messages)
return messages return messages
@classmethod def __init__(self):
def start(cls, mqtt, config): self._mqtt_callbacks = []
scheduler = BackgroundScheduler() self._update_commands = []
mqtt_callbacks = [] self._scheduler = BackgroundScheduler()
for (worker_name, worker_config) in config.items(): def register_workers(self, config):
for (worker_name, worker_config) in config['workers'].items():
module_obj = importlib.import_module("workers.%s" % worker_name) module_obj = importlib.import_module("workers.%s" % worker_name)
klass = getattr(module_obj, "%sWorker" % worker_name.title()) klass = getattr(module_obj, "%sWorker" % worker_name.title())
if module_obj.REQUIREMENTS is not None: if module_obj.REQUIREMENTS is not None:
cls._pip_install_helper(module_obj.REQUIREMENTS) self._pip_install_helper(module_obj.REQUIREMENTS)
worker_obj = klass(**worker_config['args']) worker_obj = klass(**worker_config['args'])
if 'update_interval' in worker_config: if hasattr(worker_obj, 'status_update'):
_LOGGER.debug("Added: %s with %d seconds interval" % (worker_name, worker_config['update_interval'])) _LOGGER.debug("Added: %s with %d seconds interval" % (worker_name, worker_config['update_interval']))
_WORKERS_QUEUE.put(cls.Command(worker_obj.status_update, [])) command = self.Command(worker_obj.status_update, [])
scheduler.add_job( self._update_commands.append(command)
lambda x: _WORKERS_QUEUE.put(cls.Command(worker_obj.status_update, [])), 'interval',
if 'update_interval' in worker_config:
self._scheduler.add_job(
lambda x: self._queue_command(command), 'interval',
seconds=worker_config['update_interval'], seconds=worker_config['update_interval'],
args=[worker_name] args=[worker_name]
) )
if 'topic_subscription' in worker_config: if 'topic_subscription' in worker_config:
_LOGGER.debug("Subscribing to: %s" % worker_config['topic_subscription']) _LOGGER.debug("Subscribing to: %s" % worker_config['topic_subscription'])
mqtt_callbacks.append(( self._mqtt_callbacks.append((
worker_config['topic_subscription'], worker_config['topic_subscription'],
lambda client, _ , c: _WORKERS_QUEUE.put(cls.Command(worker_obj.on_command, [c.topic, c.payload])) lambda client, _ , c: self._queue_command(self.Command(worker_obj.on_command, [c.topic, c.payload]))
)) ))
scheduler.start() for (callback_name, options) in config['topic_subcription'].items():
mqtt.callbacks_subscription(mqtt_callbacks) _LOGGER.debug("Subscribing to: %s with command: %s" % (options['topic'], callback_name))
self._mqtt_callbacks.append((
options['topic'],
lambda client, _ , c: self._queue_if_matching_payload(self.Command(getattr(self, callback_name)), c.payload, options['payload']))
)
return self
def start(self, mqtt):
self._scheduler.start()
mqtt.callbacks_subscription(self._mqtt_callbacks)
self.update_all()
def _queue_if_matching_payload(self, command, payload, expected_payload):
if payload.decode('utf-8') == expected_payload:
self._queue_command(command)
@property
def mqtt_callbacks(self):
return self._mqtt_callbacks
def update_all(self):
_LOGGER.debug("Updating all workers")
for command in self._update_commands:
self._queue_command(command)
@staticmethod
def _queue_command(command):
_WORKERS_QUEUE.put(command)
@staticmethod @staticmethod
def _pip_install_helper(package_names): def _pip_install_helper(package_names):