RabbitMQ added to the project

This commit is contained in:
atef 2025-08-05 10:02:03 +02:00
parent 26b72e24da
commit 2c13e1a2a2
6 changed files with 188 additions and 2 deletions

View File

@ -0,0 +1,15 @@
using InnovEnergy.App.GrowattCommunication.SystemConfig;
namespace InnovEnergy.App.GrowattCommunication.DataTypes;
public class Configuration
{
public Double MinimumSoC { get; set; }
public Double GridSetPoint { get; set; }
public Double MaximumDischargingCurrent { get; set; }
public Double MaximumChargingCurrent { get; set; }
public DateTime CalibrationChargeDate { get; set; }
public DateTime CalibrationDischargeDate { get; set; }
}

View File

@ -16,6 +16,7 @@
<PackageReference Include="Flurl.Http" Version="4.0.2" />
<PackageReference Include="Microsoft.Extensions.Logging" Version="7.0.0" />
<PackageReference Include="Newtonsoft.Json" Version="13.0.2" />
<PackageReference Include="RabbitMQ.Client" Version="6.6.0" />
</ItemGroup>
</Project>

View File

@ -0,0 +1,89 @@
using System.Net;
using System.Net.NetworkInformation;
using System.Net.Sockets;
using System.Text;
using System.Text.Json;
using InnovEnergy.App.GrowattCommunication.DataTypes;
namespace InnovEnergy.App.GrowattCommunication.MiddlewareClasses;
public static class MiddlewareAgent
{
private static UdpClient _udpListener = null!;
private static IPAddress? _controllerIpAddress;
private static EndPoint? _endPoint;
public static void InitializeCommunicationToMiddleware()
{
_controllerIpAddress = FindVpnIp();
if (Equals(IPAddress.None, _controllerIpAddress))
{
Console.WriteLine("There is no VPN interface, exiting...");
}
const Int32 udpPort = 9000;
_endPoint = new IPEndPoint(_controllerIpAddress, udpPort);
_udpListener = new UdpClient();
_udpListener.Client.Blocking = false;
_udpListener.Client.Bind(_endPoint);
}
private static IPAddress FindVpnIp()
{
const String interfaceName = "innovenergy";
var networkInterfaces = NetworkInterface.GetAllNetworkInterfaces();
foreach (var networkInterface in networkInterfaces)
{
if (networkInterface.Name == interfaceName)
{
var ipProps = networkInterface.GetIPProperties();
var uniCastIPs = ipProps.UnicastAddresses;
var controllerIpAddress = uniCastIPs[0].Address;
Console.WriteLine("VPN IP is: "+ uniCastIPs[0].Address);
return controllerIpAddress;
}
}
return IPAddress.None;
}
public static Configuration? SetConfigurationFile()
{
if (_udpListener.Available > 0)
{
IPEndPoint? serverEndpoint = null;
var replyMessage = "ACK";
var replyData = Encoding.UTF8.GetBytes(replyMessage);
var udpMessage = _udpListener.Receive(ref serverEndpoint);
var message = Encoding.UTF8.GetString(udpMessage);
var config = JsonSerializer.Deserialize<Configuration>(message);
if (config != null)
{
Console.WriteLine($"Received a configuration message: GridSetPoint is " + config.GridSetPoint +
", MinimumSoC is " + config.MinimumSoC );
// Send the reply to the sender's endpoint
_udpListener.Send(replyData, replyData.Length, serverEndpoint);
Console.WriteLine($"Replied to {serverEndpoint}: {replyMessage}");
return config;
}
}
if (_endPoint != null && !_endPoint.Equals(_udpListener.Client.LocalEndPoint as IPEndPoint))
{
Console.WriteLine("UDP address has changed, rebinding...");
InitializeCommunicationToMiddleware();
}
return null;
}
}

View File

@ -0,0 +1,61 @@
using System.Text;
using System.Text.Json;
using InnovEnergy.App.GrowattCommunication.DataTypes;
using RabbitMQ.Client;
namespace InnovEnergy.App.GrowattCommunication.MiddlewareClasses;
public static class RabbitMqManager
{
public static ConnectionFactory? Factory ;
public static IConnection ? Connection;
public static IModel? Channel;
public static Boolean SubscribeToQueue(StatusMessage currentSalimaxState, String? s3Bucket,String VpnServerIp)
{
try
{
//_factory = new ConnectionFactory { HostName = VpnServerIp };
Factory = new ConnectionFactory
{
HostName = VpnServerIp,
Port = 5672,
VirtualHost = "/",
UserName = "producer",
Password = "b187ceaddb54d5485063ddc1d41af66f",
};
Connection = Factory.CreateConnection();
Channel = Connection.CreateModel();
Channel.QueueDeclare(queue: "statusQueue", durable: true, exclusive: false, autoDelete: false, arguments: null);
Console.WriteLine("The controller sends its status to the middleware for the first time");
if (s3Bucket != null) InformMiddleware(currentSalimaxState);
}
catch (Exception ex)
{
Console.WriteLine("An error occurred while connecting to the RabbitMQ queue: " + ex.Message);
return false;
}
return true;
}
public static void InformMiddleware(StatusMessage status)
{
var message = JsonSerializer.Serialize(status);
var body = Encoding.UTF8.GetBytes(message);
Channel.BasicPublish(exchange: string.Empty,
routingKey: "statusQueue",
basicProperties: null,
body: body);
Console.WriteLine($"Producer sent message: {message}");
}
}

View File

@ -7,6 +7,7 @@ using System.Xml;
using Flurl.Http;
using InnovEnergy.App.GrowattCommunication.DataLogging;
using InnovEnergy.App.GrowattCommunication.ESS;
using InnovEnergy.App.GrowattCommunication.MiddlewareClasses;
using InnovEnergy.App.GrowattCommunication.SystemConfig;
using InnovEnergy.Lib.Protocols.Modbus.Channels;
using InnovEnergy.Lib.Units;
@ -17,6 +18,7 @@ using JsonSerializer = System.Text.Json.JsonSerializer;
using System.Diagnostics.CodeAnalysis;
using InnovEnergy.App.GrowattCommunication.DataTypes;
using InnovEnergy.Lib.Devices.WITGrowatt4_15K.DataType;
using static InnovEnergy.App.GrowattCommunication.MiddlewareClasses.MiddlewareAgent;
namespace InnovEnergy.App.GrowattCommunication;
@ -159,8 +161,18 @@ public static class Program
}
}
private static void ApplyConfigFile(this StatusRecord status, Configuration? config)
{
if (config == null) return;
status.Config.MinSoc = config.MinimumSoC;
status.Config.GridSetPoint = config.GridSetPoint * 1000; // converted from kW to W
status.Config.MaximumChargingCurrent = config.MaximumChargingCurrent;
status.Config.MaximumDischargingCurrent = config.MaximumDischargingCurrent; // converted from kW to W
}
private static StatusMessage GetSalimaxStateAlarm(StatusRecord record)
{
var s3Bucket = Config.Load().S3?.Bucket;
@ -235,6 +247,7 @@ public static class Program
_prevSodistoreAlarmState = currentSalimaxState.Status;
_subscribedToQueue = RabbitMqManager.SubscribeToQueue(currentSalimaxState, s3Bucket, VpnServerIp);
}
//If already subscribed to the queue and the status has been changed, update the queue
if (!subscribedNow && _subscribedToQueue && currentSalimaxState.Status != _prevSodistoreAlarmState)

View File

@ -13,6 +13,10 @@ public class Config //TODO: let IE choose from config files (Json) and connect t
private static readonly JsonSerializerOptions JsonOptions = new() { WriteIndented = true };
public required Double MinSoc { get; set; }
public required Double GridSetPoint { get; set; }
public required Double MaximumDischargingCurrent { get; set; }
public required Double MaximumChargingCurrent { get; set; }
public required S3Config? S3 { get; set; }
@ -21,6 +25,9 @@ public class Config //TODO: let IE choose from config files (Json) and connect t
public static Config Default => new()
{
MinSoc = 20,
GridSetPoint = 0,
MaximumChargingCurrent = 180,
MaximumDischargingCurrent = 180,
S3 = new()
{
Bucket = "1-3e5b3069-214a-43ee-8d85-57d72000c19d",