Files
Finlytic/FinlyticCore/Models/MqttConfiguration.cs
T

82 lines
4.0 KiB
C#

using System;
using Microsoft.Extensions.Configuration;
namespace FinlyticCore.Models;
/// <summary>
/// Represents the network and security settings used to connect to the central MQTT broker.
/// </summary>
public class MqttConfiguration
{
/// <summary>
/// Gets or sets the host address or IP of the MQTT broker.
/// </summary>
public string Host { get; set; } = string.Empty;
/// <summary>
/// Gets or sets the port number for the connection. Defaults to 1883.
/// </summary>
public int Port { get; set; } = 1883;
/// <summary>
/// Gets or sets the unique client identifier used when registering with the broker.
/// </summary>
public string ClientId { get; set; } = string.Empty;
/// <summary>
/// Gets or sets the username for authentication (optional).
/// </summary>
public string? Username { get; set; }
/// <summary>
/// Gets or sets the password for authentication (optional).
/// </summary>
public string? Password { get; set; }
/// <summary>
/// Builds an <see cref="MqttConfiguration"/> from application configuration, understanding both the
/// colon-separated key style (<c>MQTT:Host</c>, used by <c>appsettings.json</c>) and the double-underscore
/// style (<c>MQTT__Host</c>, used by container environment variables). Every one of the eight service MQTT
/// clients previously duplicated this lookup inline; centralizing it here means a new configuration key
/// (e.g. authentication) only has to be wired up once.
/// </summary>
/// <param name="configuration">The application configuration to read MQTT settings from.</param>
/// <param name="defaultClientId">
/// The service-specific client ID prefix to fall back to when no <c>MQTT:ClientId</c>/<c>MQTT__ClientId</c>
/// is configured (e.g. "FinlyticAssets"). A random suffix is always appended to the resolved client ID
/// (whether it came from configuration or from this default) to avoid the broker rejecting a duplicate
/// client ID when a service reconnects or runs multiple instances.
/// </param>
/// <returns>
/// A populated <see cref="MqttConfiguration"/>. <see cref="Username"/> and <see cref="Password"/> are left
/// <see langword="null"/> unless both are actually configured, so connections to brokers without
/// authentication enabled remain anonymous and continue to work unchanged.
/// </returns>
/// <exception cref="ArgumentNullException">Thrown when <paramref name="configuration"/> is <see langword="null"/>.</exception>
public static MqttConfiguration FromConfiguration(IConfiguration configuration, string defaultClientId)
{
ArgumentNullException.ThrowIfNull(configuration);
var host = configuration["MQTT:Host"] ?? configuration["MQTT__Host"] ?? "localhost";
var portRaw = configuration["MQTT:Port"] ?? configuration["MQTT__Port"] ?? "1883";
var port = int.TryParse(portRaw, out var parsedPort) ? parsedPort : 1883;
var configuredClientId = configuration["MQTT:ClientId"] ?? configuration["MQTT__ClientId"];
var clientId = $"{(string.IsNullOrWhiteSpace(configuredClientId) ? defaultClientId : configuredClientId)}_{Guid.NewGuid():N}";
// Optional authentication: only set Username/Password when the broker actually requires them.
// The broker this system currently runs against has no authentication configured, so leaving both
// unset here must keep the connection anonymous (see ManagedMqttClient.ConnectAsync).
var username = configuration["MQTT:Username"] ?? configuration["MQTT__Username"];
var password = configuration["MQTT:Password"] ?? configuration["MQTT__Password"];
return new MqttConfiguration
{
Host = host,
Port = port,
ClientId = clientId,
Username = string.IsNullOrWhiteSpace(username) ? null : username,
Password = string.IsNullOrWhiteSpace(password) ? null : password
};
}
}