From 6645ea6f5e9ce82937718a1bec22b7deb1acf181 Mon Sep 17 00:00:00 2001 From: Paolo Asperti Date: Tue, 19 Jan 2021 14:27:24 +0100 Subject: [PATCH] homeassistant support --- src/main.go | 2 ++ src/mqtt/mqtt.go | 11 ++++++-- src/outlets.go | 63 ++++++++++++++++++++++++++++++++++++++++++-- src/webui/mqtt_ui.go | 17 +++++++----- templates/mqtt.html | 14 ++++++++++ 5 files changed, 96 insertions(+), 11 deletions(-) diff --git a/src/main.go b/src/main.go index f7c985d..8f8499d 100644 --- a/src/main.go +++ b/src/main.go @@ -7,6 +7,8 @@ import ( "github.com/spf13/viper" ) +const version = "0.1" + func init() { viper.SetDefault("system.hostname", "openpdu") } diff --git a/src/mqtt/mqtt.go b/src/mqtt/mqtt.go index a939ce5..2112519 100644 --- a/src/mqtt/mqtt.go +++ b/src/mqtt/mqtt.go @@ -19,6 +19,7 @@ func init() { viper.SetDefault("Mqtt.Port", "1883") viper.SetDefault("Mqtt.Username", "") viper.SetDefault("Mqtt.Password", "") + viper.SetDefault("Mqtt.HomeAssistant", false) // MQTT.ERROR = log.New(os.Stdout, "[ERROR] ", 0) // MQTT.CRITICAL = log.New(os.Stdout, "[CRIT] ", 0) @@ -73,7 +74,7 @@ func Setup() { func Subscribe(topic string, handler func(MQTT.Client, MQTT.Message)) { // MQTTHandler(MQTT.Client, MQTT.Message) - MQTTclient.Subscribe(viper.GetString("Mqtt.Prefix")+"/"+topic, 1, handler) + MQTTclient.Subscribe(viper.GetString("Mqtt.Prefix")+"/switch/"+topic, 1, handler) syslog.Debug(fmt.Sprintf("MQTT subscribed to topic: %s", topic)) } @@ -90,6 +91,12 @@ func Disconnect() { func Publish(topic string, value string) { if MQTTclient.IsConnected() { - MQTTclient.Publish(viper.GetString("Mqtt.Prefix")+"/"+topic, 0, false, value) + MQTTclient.Publish(viper.GetString("Mqtt.Prefix")+"/switch/"+topic, 0, false, value) + } +} + +func PublishRoot(topic string, value string) { + if MQTTclient.IsConnected() { + MQTTclient.Publish(topic, 0, false, value) } } diff --git a/src/outlets.go b/src/outlets.go index 2e3953e..eaebbdd 100644 --- a/src/outlets.go +++ b/src/outlets.go @@ -1,6 +1,8 @@ package main import ( + "encoding/json" + "fmt" "strings" "time" @@ -49,12 +51,69 @@ func init() { func MQTTSetup() { mqtt.Setup() for o := range outlet.Outlets { - topic := outlet.Outlets[o].Channel.MQTTCommandTopic() + c := outlet.Outlets[o].Channel + topic := c.MQTTCommandTopic() if topic == "" { continue } - mqtt.Subscribe(topic, outlet.Outlets[o].Channel.MQTTHandler) + mqtt.Subscribe(topic, c.MQTTHandler) + hAssTopic := "homeassistant/switch/" + viper.GetString("Mqtt.Prefix") + "/" + fmt.Sprint(o) + "/config" + v := "" + if viper.GetBool("Mqtt.HomeAssistant") { + cfg := map[string]interface{}{ + "name": outlet.Outlets[o].Description, + "state_topic": viper.GetString("Mqtt.Prefix") + "/switch/" + c.MQTTStateTopic(), + "command_topic": viper.GetString("Mqtt.Prefix") + "/switch/" + c.MQTTCommandTopic(), + "payload_off": "off", + "payload_on": "on", + "unique_id": viper.GetString("Mqtt.Prefix") + "_" + fmt.Sprint(o), + "device": map[string]interface{}{ + "identifiers": []string{viper.GetString("Mqtt.Prefix")}, + // "name": viper.GetString("system.hostname"), + // "model": "OpenPDU", + // "sw_version": version, + // "manufacturer": "OpenPDU", + }, + } + + s, err := json.Marshal(cfg) + if err != nil { + v = "" + } else { + v = string(s) + } + } + mqtt.PublishRoot(hAssTopic, v) } + + hAssTopic := "homeassistant/switch/" + viper.GetString("Mqtt.Prefix") + "/config" + v := "" + if viper.GetBool("Mqtt.HomeAssistant") { + cfg := map[string]interface{}{ + "name": viper.GetString("system.hostname"), + // "state_topic": viper.GetString("Mqtt.Prefix") + "/switch/" + c.MQTTStateTopic(), + // "command_topic": viper.GetString("Mqtt.Prefix") + "/switch/" + c.MQTTCommandTopic(), + "payload_off": "off", + "payload_on": "on", + "unique_id": viper.GetString("Mqtt.Prefix"), + "device": map[string]interface{}{ + "identifiers": []string{viper.GetString("Mqtt.Prefix")}, + "name": viper.GetString("system.hostname"), + "model": "OpenPDU", + "sw_version": version, + "manufacturer": "OpenPDU", + }, + } + + s, err := json.Marshal(cfg) + if err != nil { + v = "" + } else { + v = string(s) + } + } + mqtt.PublishRoot(hAssTopic, v) + } func MQTTreconfigure() { diff --git a/src/webui/mqtt_ui.go b/src/webui/mqtt_ui.go index 74a7667..04533cc 100644 --- a/src/webui/mqtt_ui.go +++ b/src/webui/mqtt_ui.go @@ -23,19 +23,21 @@ func mqttPage(ctx *macaron.Context) { ctx.Data["prefix"] = viper.GetString("Mqtt.Prefix") ctx.Data["username"] = viper.GetString("Mqtt.Username") ctx.Data["password"] = viper.GetString("Mqtt.Password") + ctx.Data["homeassistant"] = viper.GetString("Mqtt.homeassistant") ctx.Data["schemas"] = []string{"tcp", "ssl", "ws"} ctx.HTML(200, "mqtt") } type MQTTPostForm struct { - Schema string `form:"schema" binding:"Required"` - Host string `form:"host" binding:"Required"` - Port string `form:"port" binding:"Required"` - Prefix string `form:"prefix" binding:"Required"` - ClientID string `form:"clientid" binding:"Required"` - Username string `form:"username"` - Password string `form:"password"` + Schema string `form:"schema" binding:"Required"` + Host string `form:"host" binding:"Required"` + Port string `form:"port" binding:"Required"` + Prefix string `form:"prefix" binding:"Required"` + ClientID string `form:"clientid" binding:"Required"` + Username string `form:"username"` + Password string `form:"password"` + HomeAssistant bool `form:"homeassistant"` } func mqttPost(ctx *macaron.Context, f MQTTPostForm) { @@ -57,6 +59,7 @@ func mqttPost(ctx *macaron.Context, f MQTTPostForm) { viper.Set("Mqtt.Prefix", strings.TrimSpace(f.Prefix)) viper.Set("Mqtt.Username", strings.TrimSpace(f.Username)) viper.Set("Mqtt.Password", f.Password) + viper.Set("Mqtt.HomeAssistant", f.HomeAssistant) viper.WriteConfig() diff --git a/templates/mqtt.html b/templates/mqtt.html index b6968f6..7a45399 100644 --- a/templates/mqtt.html +++ b/templates/mqtt.html @@ -92,6 +92,20 @@ +
+ +
+
+ +
+
+