From 666ec3b794b2eaaf0d0203b41cd1a1def2a4f8eb Mon Sep 17 00:00:00 2001 From: hsakoh <20980395+hsakoh@users.noreply.github.com> Date: Sat, 10 Aug 2024 05:07:05 +0900 Subject: [PATCH] - Changed the base image of the add-on from [Docker Hub](https://hub.docker.com/r/homeassistant/amd64-base/tags) to [GitHub Container Registry](https://github.com/home-assistant/docker-base/pkgs/container/amd64-base). - Updated the add-on runtime to .NET 8 LTS. - Nuget package update --- README.md | 2 +- _build_on_haos/Dockerfile | 4 +- _build_on_haos/config.yaml | 2 +- _compile_self/Dockerfile | 2 +- _compile_self/config.yaml | 2 +- src/BRouteController/BRouteController.csproj | 13 +- .../BRouteControllerService.cs | 4 +- src/BRouteMqttApp/BRouteMqttApp.csproj | 2 +- src/BRouteMqttApp/Program.cs | 4 +- src/BRouteMqttApp/Worker.cs | 119 ++++++++---------- .../EchoDotNetLite.Specifications.csproj | 2 +- .../EchoDotNetLite/EchoDotNetLite.csproj | 4 +- .../EchoDotNetLiteSkstackIpBridge.csproj | 2 +- .../SkstackIpDotNet/SkstackIpDotNet.csproj | 6 +- .../ConfigurationExtensions.cs | 6 +- .../HomeAssistantAddOn.Core.csproj | 6 +- .../HomeAssistantAddOn.Core/Utility.cs | 13 ++ .../DependencyInjectionExtensions.cs | 2 +- .../HomeAssistantAddOn.Mqtt.csproj | 16 +-- .../HomeAssistantAddOn.Mqtt/MqttService.cs | 32 ++++- .../HomeAssistantAddOn.Mqtt/SupervisorApi.cs | 14 ++- 21 files changed, 146 insertions(+), 111 deletions(-) create mode 100644 src/HomeAssistant/HomeAssistantAddOn.Core/Utility.cs diff --git a/README.md b/README.md index 65494db..06a94d5 100644 --- a/README.md +++ b/README.md @@ -90,6 +90,6 @@ Enhanced HAN」※2 対応のものは
コマンドの引数や使い方が * Windows上では、AddOnの構成ファイル`/data/options.json`にアクセスできないと思われるので、
`appsettings.Development.json`に構成を行ってください。 * 発行時は、ridで`win-x64`等を指定してください。
[.NET Runtime Identifier (RID) カタログ | Microsoft Learn](https://learn.microsoft.com/ja-jp/dotnet/core/rid-catalog) * [.NET での汎用ホスト 既定の builder 設定](https://learn.microsoft.com/ja-jp/dotnet/core/extensions/generic-host#default-builder-settings)の通り、
環境変数やコマンドライン引数からも読み込み可能です
(階層は`BRoute:Id`等コロンを含めて表現が必要です) -* Wi-SUN USBスティックとのやり取りは、[NuGet Gallery | System.IO.Ports 6.0.0](https://www.nuget.org/packages/System.IO.Ports/6.0.0)を使用しています。 +* Wi-SUN USBスティックとのやり取りは、[NuGet Gallery | System.IO.Ports 8.0.0](https://www.nuget.org/packages/System.IO.Ports/8.0.0)を使用しています。 * Linux等向けは動作環境毎の発行が必要となる場合があります。(`linux-arm64`と`linux-musl-arm64`の違いとか) * 参考:[System.IO.Ports.SerialPort not working on Linux arm64 · Issue #74332 · dotnet/runtime](https://github.com/dotnet/runtime/issues/74332) \ No newline at end of file diff --git a/_build_on_haos/Dockerfile b/_build_on_haos/Dockerfile index 374af5a..39245a8 100644 --- a/_build_on_haos/Dockerfile +++ b/_build_on_haos/Dockerfile @@ -1,5 +1,5 @@ ARG BUILD_FROM -FROM mcr.microsoft.com/dotnet/sdk:6.0-alpine as builder +FROM mcr.microsoft.com/dotnet/sdk:8.0-alpine as builder WORKDIR /src COPY /src . @@ -15,7 +15,7 @@ ENV BUILD_ARCH=$BUILD_ARCH # Install requirements for add-on RUN \ apk add --no-cache \ - gcompat bash icu-libs krb5-libs libgcc libintl libssl1.1 libstdc++ zlib dotnet6-runtime + bash ca-certificates-bundle libgcc libssl3 libstdc++ zlib dotnet8-runtime COPY --from=builder /app/$BUILD_ARCH /app ENTRYPOINT ["/app/BRouteMqttApp"] \ No newline at end of file diff --git a/_build_on_haos/config.yaml b/_build_on_haos/config.yaml index 067c87e..640ae54 100644 --- a/_build_on_haos/config.yaml +++ b/_build_on_haos/config.yaml @@ -1,6 +1,6 @@ name: "BRoute-Mqtt" description: "Wi-SUNドングル/ECHONETLiteプロトコルを通じて、低圧スマート電力量メータをHome AssistantのMQTTにデバイス/センサーとして統合するアドオン" -version: "1.0.1" +version: "1.0.4" slug: "broute_mqtt" url: "https://github.com/hsakoh/broutemqtt-mqtt" startup: application diff --git a/_compile_self/Dockerfile b/_compile_self/Dockerfile index c81ef9f..cba7bf9 100644 --- a/_compile_self/Dockerfile +++ b/_compile_self/Dockerfile @@ -7,7 +7,7 @@ ENV BUILD_ARCH=$BUILD_ARCH # Install requirements for add-on RUN \ apk add --no-cache \ - gcompat bash icu-libs krb5-libs libgcc libintl libssl1.1 libstdc++ zlib dotnet6-runtime + bash ca-certificates-bundle libgcc libssl3 libstdc++ zlib dotnet8-runtime COPY /$BUILD_ARCH /app ENTRYPOINT ["/app/BRouteMqttApp"] \ No newline at end of file diff --git a/_compile_self/config.yaml b/_compile_self/config.yaml index 067c87e..640ae54 100644 --- a/_compile_self/config.yaml +++ b/_compile_self/config.yaml @@ -1,6 +1,6 @@ name: "BRoute-Mqtt" description: "Wi-SUNドングル/ECHONETLiteプロトコルを通じて、低圧スマート電力量メータをHome AssistantのMQTTにデバイス/センサーとして統合するアドオン" -version: "1.0.1" +version: "1.0.4" slug: "broute_mqtt" url: "https://github.com/hsakoh/broutemqtt-mqtt" startup: application diff --git a/src/BRouteController/BRouteController.csproj b/src/BRouteController/BRouteController.csproj index 5055743..b47afeb 100644 --- a/src/BRouteController/BRouteController.csproj +++ b/src/BRouteController/BRouteController.csproj @@ -1,17 +1,18 @@  - net6.0 + net8.0 enable enable + linux-musl-arm64;linux-musl-x64 - - - - - + + + + + diff --git a/src/BRouteController/BRouteControllerService.cs b/src/BRouteController/BRouteControllerService.cs index fb07259..9f4db4c 100644 --- a/src/BRouteController/BRouteControllerService.cs +++ b/src/BRouteController/BRouteControllerService.cs @@ -262,7 +262,9 @@ private async Task ReadAllPropertyMapAsync(CancellationToken ct) } } +#pragma warning disable IDE0060 // 未使用のパラメーターを削除します private async Task<(EchoNode node, EchoObjectInstance device)> ReadAllPropertiesAsync(CancellationToken cs) +#pragma warning restore IDE0060 // 未使用のパラメーターを削除します { //Bルートなので、低圧スマート電力量メータ以外のデバイスは存在しない前提 var node = _echoClient.NodeList.First(); @@ -272,7 +274,7 @@ private async Task ReadAllPropertyMapAsync(CancellationToken ct) //まとめてもできるけど、大量に指定するとこけるのでプロパティ毎に foreach (var prop in device.GETProperties) { - await ReadPropertyWithRetry(node, device, new EchoPropertyInstance[] { prop }); + await ReadPropertyWithRetry(node, device, [prop]); } return (node, device); } diff --git a/src/BRouteMqttApp/BRouteMqttApp.csproj b/src/BRouteMqttApp/BRouteMqttApp.csproj index 71e8044..d5cad34 100644 --- a/src/BRouteMqttApp/BRouteMqttApp.csproj +++ b/src/BRouteMqttApp/BRouteMqttApp.csproj @@ -1,7 +1,7 @@  - net6.0 + net8.0 enable enable linux-musl-arm64;linux-musl-x64 diff --git a/src/BRouteMqttApp/Program.cs b/src/BRouteMqttApp/Program.cs index fab7f47..996f284 100644 --- a/src/BRouteMqttApp/Program.cs +++ b/src/BRouteMqttApp/Program.cs @@ -15,12 +15,12 @@ public static void Main(string[] args) { var config = context.Configuration.Get(); loggingBuilder - .AddFilter(string.Empty, config.LogLevel) + .AddFilter(string.Empty, config!.LogLevel) .AddSimpleConsole(options => { options.IncludeScopes = true; options.SingleLine = true; - options.TimestampFormat = "HH:mm:ss "; + options.TimestampFormat = "yyyy/MM/dd HH:mm:ss "; }); }) diff --git a/src/BRouteMqttApp/Worker.cs b/src/BRouteMqttApp/Worker.cs index 5e05c13..fb5972a 100644 --- a/src/BRouteMqttApp/Worker.cs +++ b/src/BRouteMqttApp/Worker.cs @@ -3,27 +3,16 @@ namespace BRouteMqttApp; -public class Worker : BackgroundService -{ - private readonly ILogger _logger; - private readonly BRouteControllerService _bRouteControllerService; - private readonly MqttService _mqttService; - - public Worker( - ILogger logger +public class Worker( + ILogger logger , BRouteControllerService bRouteControllerService , MqttService mqttService - ) - { - _logger = logger; - _bRouteControllerService = bRouteControllerService; - _mqttService = mqttService; - } - + ) : BackgroundService +{ public override async Task StartAsync(CancellationToken cancellationToken) { - await _mqttService.StartAsync(); - await _bRouteControllerService.InitalizeAsync(cancellationToken); + await mqttService.StartAsync(); + await bRouteControllerService.InitalizeAsync(cancellationToken); await PublishDeviceConfigsAsync(); @@ -34,27 +23,27 @@ public override async Task StartAsync(CancellationToken cancellationToken) await PublishDeviceStaticStatusAsync(); SubscribeCommandTopic(); - _bRouteControllerService.ActivePropertiesReadedCallback = PublishDeviceActiveStatusAsync; - _bRouteControllerService.PassivePropertiesReadedCallback = PublishDevicePassiveStatusAsync; - _bRouteControllerService.PassivePropertiesOnTimeCallback = PublishDevicePassiveOnTimeStatusAsync; + bRouteControllerService.ActivePropertiesReadedCallback = PublishDeviceActiveStatusAsync; + bRouteControllerService.PassivePropertiesReadedCallback = PublishDevicePassiveStatusAsync; + bRouteControllerService.PassivePropertiesOnTimeCallback = PublishDevicePassiveOnTimeStatusAsync; await base.StartAsync(cancellationToken); } protected override async Task ExecuteAsync(CancellationToken stoppingToken) { - await _bRouteControllerService.PollAsync(stoppingToken); + await bRouteControllerService.PollAsync(stoppingToken); } public override async Task StopAsync(CancellationToken cancellationToken) { - await _mqttService.StopAsync(); + await mqttService.StopAsync(); await base.StopAsync(cancellationToken); } #region Configure Senser private async Task PublishDeviceConfigsAsync() { - var serial = _bRouteControllerService.Meter.製造番号!; + var serial = bRouteControllerService.Meter.製造番号!; await PublishSensorConfigAsync(serial, "placement", "設置場所", "static", icon: "mdi:map-marker"); await PublishSensorConfigAsync(serial, "version", "規格Version情報", "static", icon: "mdi:information"); await PublishSensorConfigAsync(serial, "makercode", "メーカコード", "static", icon: "mdi:factory"); @@ -106,7 +95,7 @@ private async Task PublishSensorConfigAsync( name = nameof(低圧スマート電力量メータ), }, }; - await _mqttService.PublishAsync($"homeassistant/sensor/{type}_{serial}/config", payload, true); + await mqttService.PublishAsync($"homeassistant/sensor/{type}_{serial}/config", payload, true); } private async Task SendButtonConfigAsync(string serial, string type, string name, string device_class) @@ -125,7 +114,7 @@ private async Task SendButtonConfigAsync(string serial, string type, string name name = nameof(低圧スマート電力量メータ), }, }; - await _mqttService.PublishAsync($"homeassistant/button/btn_{type}_{serial}/config", payload, true); + await mqttService.PublishAsync($"homeassistant/button/btn_{type}_{serial}/config", payload, true); } #endregion @@ -133,88 +122,88 @@ private async Task SendButtonConfigAsync(string serial, string type, string name public async Task PublishDeviceStaticStatusAsync() { - var serial = _bRouteControllerService.Meter.製造番号!; + var serial = bRouteControllerService.Meter.製造番号!; await SendSensorStateAsync(serial, "static", new { - placement = _bRouteControllerService.Meter.設置場所, - version = _bRouteControllerService.Meter.規格Version情報, - makercode = _bRouteControllerService.Meter.メーカコード, + placement = bRouteControllerService.Meter.設置場所, + version = bRouteControllerService.Meter.規格Version情報, + makercode = bRouteControllerService.Meter.メーカコード, serialnumber = serial, }); - _logger.LogInformation("ステータス(静的)通知 {a},{b},{c},{d}", - _bRouteControllerService.Meter.設置場所, - _bRouteControllerService.Meter.規格Version情報, - _bRouteControllerService.Meter.メーカコード, + logger.LogInformation("ステータス(静的)通知 {a},{b},{c},{d}", + bRouteControllerService.Meter.設置場所, + bRouteControllerService.Meter.規格Version情報, + bRouteControllerService.Meter.メーカコード, serial ); } public async Task PublishDeviceActiveStatusAsync() { - var serial = _bRouteControllerService.Meter.製造番号!; + var serial = bRouteControllerService.Meter.製造番号!; await SendSensorStateAsync(serial, "active", new { - instantaneous_current_r = _bRouteControllerService.Meter.瞬時電流計測値?.r, - instantaneous_current_t = _bRouteControllerService.Meter.瞬時電流計測値?.t, - instantaneous_electric_power = _bRouteControllerService.Meter.瞬時電力計測値, - timestamp = _bRouteControllerService.Meter.現在年月日時刻 + instantaneous_current_r = bRouteControllerService.Meter.瞬時電流計測値?.r, + instantaneous_current_t = bRouteControllerService.Meter.瞬時電流計測値?.t, + instantaneous_electric_power = bRouteControllerService.Meter.瞬時電力計測値, + timestamp = bRouteControllerService.Meter.現在年月日時刻 }); - _logger.LogInformation("ステータス(瞬時)通知 {r}A,{t}A,{e}W,{time}", - _bRouteControllerService.Meter.瞬時電流計測値?.r, - _bRouteControllerService.Meter.瞬時電流計測値?.t, - _bRouteControllerService.Meter.瞬時電力計測値, - _bRouteControllerService.Meter.現在年月日時刻 + logger.LogInformation("ステータス(瞬時)通知 {r}A,{t}A,{e}W,{time}", + bRouteControllerService.Meter.瞬時電流計測値?.r, + bRouteControllerService.Meter.瞬時電流計測値?.t, + bRouteControllerService.Meter.瞬時電力計測値, + bRouteControllerService.Meter.現在年月日時刻 ); } public async Task PublishDevicePassiveStatusAsync() { - var serial = _bRouteControllerService.Meter.製造番号!; + var serial = bRouteControllerService.Meter.製造番号!; await SendSensorStateAsync(serial, "passive", new { - cumulative_normal = _bRouteControllerService.Meter.積算電力量計測値_正方向計測値, - cumulative_reverse = _bRouteControllerService.Meter.積算電力量計測値_逆方向計測値, - timestamp = _bRouteControllerService.Meter.現在年月日時刻 + cumulative_normal = bRouteControllerService.Meter.積算電力量計測値_正方向計測値, + cumulative_reverse = bRouteControllerService.Meter.積算電力量計測値_逆方向計測値, + timestamp = bRouteControllerService.Meter.現在年月日時刻 }); - _logger.LogInformation("ステータス(積算)通知 {n}W,{r}W,{time}", - _bRouteControllerService.Meter.積算電力量計測値_正方向計測値, - _bRouteControllerService.Meter.積算電力量計測値_逆方向計測値, - _bRouteControllerService.Meter.現在年月日時刻 + logger.LogInformation("ステータス(積算)通知 {n}W,{r}W,{time}", + bRouteControllerService.Meter.積算電力量計測値_正方向計測値, + bRouteControllerService.Meter.積算電力量計測値_逆方向計測値, + bRouteControllerService.Meter.現在年月日時刻 ); } public async Task PublishDevicePassiveOnTimeStatusAsync() { - var serial = _bRouteControllerService.Meter.製造番号!; + var serial = bRouteControllerService.Meter.製造番号!; await SendSensorStateAsync(serial, "passive", new { - cumulative_normal = _bRouteControllerService.Meter.定時積算電力量計測値_正方向計測値?.kWh, - cumulative_reverse = _bRouteControllerService.Meter.定時積算電力量計測値_逆方向計測値?.kWh, - timestamp = _bRouteControllerService.Meter.定時積算電力量計測値_逆方向計測値?.datetime, + cumulative_normal = bRouteControllerService.Meter.定時積算電力量計測値_正方向計測値?.kWh, + cumulative_reverse = bRouteControllerService.Meter.定時積算電力量計測値_逆方向計測値?.kWh, + timestamp = bRouteControllerService.Meter.定時積算電力量計測値_逆方向計測値?.datetime, }); - _logger.LogInformation("ステータス(積算-定時)通知 {n}W,{r}W,{time}", - _bRouteControllerService.Meter.定時積算電力量計測値_正方向計測値?.kWh, - _bRouteControllerService.Meter.定時積算電力量計測値_逆方向計測値?.kWh, - _bRouteControllerService.Meter.定時積算電力量計測値_逆方向計測値?.datetime + logger.LogInformation("ステータス(積算-定時)通知 {n}W,{r}W,{time}", + bRouteControllerService.Meter.定時積算電力量計測値_正方向計測値?.kWh, + bRouteControllerService.Meter.定時積算電力量計測値_逆方向計測値?.kWh, + bRouteControllerService.Meter.定時積算電力量計測値_逆方向計測値?.datetime ); } private async Task SendSensorStateAsync( string serial, string subTopic, object payload) { - await _mqttService.PublishAsync($"homeassistant/sensor/{serial}/state/{subTopic}", payload, false); + await mqttService.PublishAsync($"homeassistant/sensor/{serial}/state/{subTopic}", payload, false); } #endregion private void SubscribeCommandTopic() { - var serial = _bRouteControllerService.Meter.製造番号!; - _mqttService.Subscribe($"homeassistant/button/{serial}/cmd", async (payload) => + var serial = bRouteControllerService.Meter.製造番号!; + mqttService.Subscribe($"homeassistant/button/{serial}/cmd", async (payload) => { - _logger.LogInformation("コマンドを受信:{payload}", payload); + logger.LogInformation("コマンドを受信:{payload}", payload); if (payload == "active") { - await _bRouteControllerService.ReadActivePropertiesAsync(); + await bRouteControllerService.ReadActivePropertiesAsync(); } else if (payload == "passive") { - await _bRouteControllerService.ReadPassivePropertiesAsync(); + await bRouteControllerService.ReadPassivePropertiesAsync(); } }); } diff --git a/src/EchonetLite/EchoDotNetLite.Specifications/EchoDotNetLite.Specifications.csproj b/src/EchonetLite/EchoDotNetLite.Specifications/EchoDotNetLite.Specifications.csproj index 0bd0a57..4edee56 100644 --- a/src/EchonetLite/EchoDotNetLite.Specifications/EchoDotNetLite.Specifications.csproj +++ b/src/EchonetLite/EchoDotNetLite.Specifications/EchoDotNetLite.Specifications.csproj @@ -1,7 +1,7 @@ - net6.0 + net8.0 diff --git a/src/EchonetLite/EchoDotNetLite/EchoDotNetLite.csproj b/src/EchonetLite/EchoDotNetLite/EchoDotNetLite.csproj index 421f479..3e40d9b 100644 --- a/src/EchonetLite/EchoDotNetLite/EchoDotNetLite.csproj +++ b/src/EchonetLite/EchoDotNetLite/EchoDotNetLite.csproj @@ -1,11 +1,11 @@ - net6.0 + net8.0 - + diff --git a/src/EchonetLite/EchoDotNetLiteSkstackIpBridge/EchoDotNetLiteSkstackIpBridge.csproj b/src/EchonetLite/EchoDotNetLiteSkstackIpBridge/EchoDotNetLiteSkstackIpBridge.csproj index c32595b..1bee935 100644 --- a/src/EchonetLite/EchoDotNetLiteSkstackIpBridge/EchoDotNetLiteSkstackIpBridge.csproj +++ b/src/EchonetLite/EchoDotNetLiteSkstackIpBridge/EchoDotNetLiteSkstackIpBridge.csproj @@ -1,7 +1,7 @@ - net6.0 + net8.0 diff --git a/src/EchonetLite/SkstackIpDotNet/SkstackIpDotNet.csproj b/src/EchonetLite/SkstackIpDotNet/SkstackIpDotNet.csproj index 0b0fd62..34ef67c 100644 --- a/src/EchonetLite/SkstackIpDotNet/SkstackIpDotNet.csproj +++ b/src/EchonetLite/SkstackIpDotNet/SkstackIpDotNet.csproj @@ -1,14 +1,14 @@ - net6.0 + net8.0 linux-musl-arm64;linux-musl-x64 - + - + diff --git a/src/HomeAssistant/HomeAssistantAddOn.Core/ConfigurationExtensions.cs b/src/HomeAssistant/HomeAssistantAddOn.Core/ConfigurationExtensions.cs index 62efb59..30d7cf8 100644 --- a/src/HomeAssistant/HomeAssistantAddOn.Core/ConfigurationExtensions.cs +++ b/src/HomeAssistant/HomeAssistantAddOn.Core/ConfigurationExtensions.cs @@ -1,9 +1,11 @@ -namespace Microsoft.Extensions.Configuration; +using HomeAssistantAddOn.Core; + +namespace Microsoft.Extensions.Configuration; public static class ConfigurationExtensions { public static IConfigurationBuilder AddHomeAssistantAddOnConfig(this IConfigurationBuilder builder) { - return builder.AddJsonFile("/data/options.json", optional: true); + return builder.AddJsonFile($"{Utility.GetBaseDataDirectory()}options.json", optional: true); } } \ No newline at end of file diff --git a/src/HomeAssistant/HomeAssistantAddOn.Core/HomeAssistantAddOn.Core.csproj b/src/HomeAssistant/HomeAssistantAddOn.Core/HomeAssistantAddOn.Core.csproj index b082033..d9a1c52 100644 --- a/src/HomeAssistant/HomeAssistantAddOn.Core/HomeAssistantAddOn.Core.csproj +++ b/src/HomeAssistant/HomeAssistantAddOn.Core/HomeAssistantAddOn.Core.csproj @@ -1,14 +1,14 @@ - net6.0 + net8.0 enable enable - - + + diff --git a/src/HomeAssistant/HomeAssistantAddOn.Core/Utility.cs b/src/HomeAssistant/HomeAssistantAddOn.Core/Utility.cs new file mode 100644 index 0000000..33438b9 --- /dev/null +++ b/src/HomeAssistant/HomeAssistantAddOn.Core/Utility.cs @@ -0,0 +1,13 @@ +namespace HomeAssistantAddOn.Core; + +public static class Utility +{ + public static string GetBaseDataDirectory() + { + if (Environment.GetEnvironmentVariables().Contains("OVERRIDE_DATA_PATH")) + { + return Environment.GetEnvironmentVariable("OVERRIDE_DATA_PATH")!; + } + return "/data/"; + } +} diff --git a/src/HomeAssistant/HomeAssistantAddOn.Mqtt/DependencyInjectionExtensions.cs b/src/HomeAssistant/HomeAssistantAddOn.Mqtt/DependencyInjectionExtensions.cs index 2e57ada..f2e5e67 100644 --- a/src/HomeAssistant/HomeAssistantAddOn.Mqtt/DependencyInjectionExtensions.cs +++ b/src/HomeAssistant/HomeAssistantAddOn.Mqtt/DependencyInjectionExtensions.cs @@ -19,7 +19,7 @@ public static IServiceCollection AddHomeAssistantMqtt( services.AddHttpClient(nameof(SupervisorApi), httpClient => { httpClient.BaseAddress = new Uri("http://supervisor/"); - httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue(Environment.GetEnvironmentVariable("SUPERVISOR_TOKEN")!); + httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue(Environment.GetEnvironmentVariable("SUPERVISOR_TOKEN")! ?? "invalid"); }); return services; } diff --git a/src/HomeAssistant/HomeAssistantAddOn.Mqtt/HomeAssistantAddOn.Mqtt.csproj b/src/HomeAssistant/HomeAssistantAddOn.Mqtt/HomeAssistantAddOn.Mqtt.csproj index 6718c30..1abfdca 100644 --- a/src/HomeAssistant/HomeAssistantAddOn.Mqtt/HomeAssistantAddOn.Mqtt.csproj +++ b/src/HomeAssistant/HomeAssistantAddOn.Mqtt/HomeAssistantAddOn.Mqtt.csproj @@ -1,19 +1,19 @@  - net6.0 + net8.0 enable enable - - - - - - - + + + + + + + diff --git a/src/HomeAssistant/HomeAssistantAddOn.Mqtt/MqttService.cs b/src/HomeAssistant/HomeAssistantAddOn.Mqtt/MqttService.cs index ae95b85..445a36b 100644 --- a/src/HomeAssistant/HomeAssistantAddOn.Mqtt/MqttService.cs +++ b/src/HomeAssistant/HomeAssistantAddOn.Mqtt/MqttService.cs @@ -8,6 +8,7 @@ using Newtonsoft.Json; using System.Collections.Concurrent; using System.Reflection; +using System.Security.Authentication; namespace HomeAssistantAddOn.Mqtt; public class MqttService : IDisposable @@ -34,6 +35,11 @@ public MqttService( public async Task StartAsync() { + if (_mqttClient.IsStarted) + { + _logger.LogDebug("Already Started"); + return; + } var options = _optionsMonitor.CurrentValue; SupervisorApi.ServiceMqtt? serviceMqtt = null; if (options.AutoConfig) @@ -61,7 +67,9 @@ public async Task StartAsync() } if (serviceMqtt.Ssl) { - builder.WithTls(); + builder.WithTlsOptions(opt => { + opt.WithSslProtocols(SslProtocols.Tls12); + }); } } else @@ -75,7 +83,9 @@ public async Task StartAsync() } if (options.Tls) { - builder.WithTls(); + builder.WithTlsOptions(opt => { + opt.WithSslProtocols(SslProtocols.Tls12); + }); } } }) @@ -86,6 +96,11 @@ public async Task StartAsync() public async Task StopAsync() { + foreach(var subscription in _subscriptions) + { + await _mqttClient.UnsubscribeAsync(subscription.Key); + } + _subscriptions.Clear(); await _mqttClient.StopAsync(); _logger.LogDebug("Stop"); } @@ -96,7 +111,7 @@ public void Subscribe(string topic, Func subscribeTask) , _ => { _mqttClient.SubscribeAsync(topic); - return new List> { subscribeTask }; + return [subscribeTask]; } , (_, list) => { @@ -129,6 +144,17 @@ await _mqttClient.EnqueueAsync(new MqttApplicationMessageBuilder() _logger.LogDebug("Publish {topic}", topic); } + public async Task PublishAsync(string topic, string jsonPayload, bool retain = false) + { + await _mqttClient.EnqueueAsync(new MqttApplicationMessageBuilder() + .WithTopic(topic) + .WithPayload(jsonPayload) + .WithQualityOfServiceLevel(MqttQualityOfServiceLevel.AtLeastOnce) + .WithRetainFlag(retain) + .Build()); + _logger.LogDebug("Publish {topic}", topic); + } + public void Dispose() { _mqttClient?.Dispose(); diff --git a/src/HomeAssistant/HomeAssistantAddOn.Mqtt/SupervisorApi.cs b/src/HomeAssistant/HomeAssistantAddOn.Mqtt/SupervisorApi.cs index b45f603..86b5e69 100644 --- a/src/HomeAssistant/HomeAssistantAddOn.Mqtt/SupervisorApi.cs +++ b/src/HomeAssistant/HomeAssistantAddOn.Mqtt/SupervisorApi.cs @@ -3,13 +3,9 @@ namespace HomeAssistantAddOn.Mqtt; -public class SupervisorApi +public class SupervisorApi(IHttpClientFactory httpClientFactory) { - private readonly HttpClient _httpClient; - public SupervisorApi(IHttpClientFactory httpClientFactory) - { - _httpClient = httpClientFactory.CreateClient(nameof(SupervisorApi)); - } + private readonly HttpClient _httpClient = httpClientFactory.CreateClient(nameof(SupervisorApi)); public async Task?> GetServicesMqtt() { @@ -45,4 +41,10 @@ public class ServiceMqtt [JsonPropertyName("addon")] public string Addon { get; set; } = default!; } + + public class AddonInfo + { + [JsonPropertyName("ingress_entry")] + public string IngressEntry { get; set; } = default!; + } } \ No newline at end of file