make AmptStatus implement IMppt

This commit is contained in:
ig 2023-08-25 17:15:46 +02:00
parent 418bac6a6a
commit 728cb7aefb
7 changed files with 24 additions and 134 deletions

View File

@ -9,6 +9,7 @@
<ProjectReference Include="../../Protocols/Modbus/Modbus.csproj" />
<ProjectReference Include="../../Utils/Utils.csproj" />
<ProjectReference Include="../../Units/Units.csproj" />
<ProjectReference Include="../../StatusApi/StatusApi.csproj" />
</ItemGroup>
</Project>

View File

@ -1,90 +0,0 @@
// using InnovEnergy.Lib.Protocols.Modbus.Channels;
// using InnovEnergy.Lib.Protocols.Modbus.Clients;
// using InnovEnergy.Lib.Protocols.Modbus.Conversions;
// using InnovEnergy.Lib.Protocols.Modbus.Slaves;
// using InnovEnergy.Lib.Units.Composite;
//
// namespace InnovEnergy.Lib.Devices.AMPT;
//
// public class AmptCommunicationUnit : ModbusDevice<CommunicationUnitRegisters>
// {
//
// private const UInt16 RegistersPerDevice = 16;
// private const UInt16 FirstDeviceOffset = 85;
//
//
// public AmptCommunicationUnit(String hostname, UInt16 port = 502, Byte slaveAddress = 1) : this
// (
// channel: new TcpChannel(hostname, port),
// slaveAddress
// )
// {}
//
//
// public AmptCommunicationUnit(Channel channel, Byte slaveAddress) : this
// (
// client: new ModbusTcpClient(channel, slaveAddress)
// )
// {}
//
// public AmptCommunicationUnit(ModbusClient client) : base(client)
// {
// }
//
//
// private AmptCommunicationUnitStatus TryReadStatus()
// {
// var r = new ModbusRegisters(116, Modbus.ReadHoldingRegisters(1, 116).ToArray()) ; // TODO
//
// var currentFactor = Pow(10.0m, r.GetInt16(73));
// var voltageFactor = Pow(10.0m, r.GetInt16(74));
// var energyFactor = Pow(10.0m, r.GetInt16(76) + 3); // +3 => converted from Wh to kWh
// var nbrOfDevices = r.GetUInt16(78);
//
// var devices = Enumerable
// .Range(0, nbrOfDevices)
// .Select(ReadDeviceStatus)
// .ToList();
//
// return new AmptCommunicationUnitStatus
// {
// Sid = r.GetUInt32(1),
// IdSunSpec = r.GetUInt16(3),
// Manufacturer = r.GetString(5, 16),
// Model = r.GetString(21, 16),
// Version = r.GetString(45, 8),
// SerialNumber = r.GetString(53, 16),
// DeviceAddress = r.GetInt16(69),
// IdVendor = r.GetUInt16(71),
// Devices = devices
// };
//
// AmptStatus ReadDeviceStatus(Int32 deviceNumber)
// {
// var baseAddress = (UInt16)(FirstDeviceOffset + deviceNumber * RegistersPerDevice); // base address
//
// return new AmptStatus
// {
// Dc = new DcBus
// {
// Voltage = r.GetUInt32((UInt16)(baseAddress + 6)) * voltageFactor,
// Current = r.GetUInt16((UInt16)(baseAddress + 5)) * currentFactor
// },
// Strings = new DcBus[]
// {
// new()
// {
// Voltage = r.GetUInt32((UInt16)(baseAddress + 8)) * voltageFactor,
// Current = r.GetUInt16((UInt16)(baseAddress + 14)) * currentFactor
// },
// new()
// {
// Voltage = r.GetUInt32((UInt16)(baseAddress + 9)) * voltageFactor,
// Current = r.GetUInt16((UInt16)(baseAddress + 15)) * currentFactor
// }
// },
// ProductionToday = r.GetUInt32((UInt16)(baseAddress + 12)) * energyFactor,
// };
// }
// }
// }

View File

@ -1,6 +1,7 @@
using InnovEnergy.Lib.Protocols.Modbus.Channels;
using InnovEnergy.Lib.Protocols.Modbus.Clients;
using InnovEnergy.Lib.Protocols.Modbus.Slaves;
using InnovEnergy.Lib.Time.Unix;
using InnovEnergy.Lib.Units.Composite;
using InnovEnergy.Lib.Utils;
@ -25,22 +26,25 @@ public class AmptDevices
_StringOptimizers = StringOptimizers(modbusClient);
}
public AmptStatus Read()
public AmptStatus? Read()
{
CommunicationUnitRegisters? cuStatus = null;
try
{
cuStatus = _CommunicationUnit.Read();
return TryRead();
}
catch (Exception e)
{
Console.WriteLine("Failed to read Ampt data \n" + e.Message);
// TODO: log
return null;
}
}
public AmptStatus TryRead()
{
var cuStatus = _CommunicationUnit.Read();
// CommunicationUnit knows how many StringOptimizers are connected
var nStringOptimizers = cuStatus?.NumberOfStringOptimizers ?? 0;
var nStringOptimizers = cuStatus.NumberOfStringOptimizers;
// hardcoded: every SO has 2 strings (produced like this by AMPT)
var nStrings = nStringOptimizers * 2;
@ -64,7 +68,11 @@ public class AmptDevices
// flatten the 2 strings of each SO into one array
var strings = soStati.SelectMany(GetStrings).ToArray(nStrings);
return new AmptStatus(dc, strings);
return new AmptStatus
{
Dc = dc,
Strings = strings
};
}

View File

@ -1,38 +1,11 @@
using InnovEnergy.Lib.StatusApi.DeviceTypes;
using InnovEnergy.Lib.Units.Composite;
namespace InnovEnergy.Lib.Devices.AMPT;
public class AmptStatus
public class AmptStatus : IMppt
{
public AmptStatus(DcBus? dc, IReadOnlyList<DcBus> strings)
{
Dc = dc;
Strings = strings;
}
public DcBus? Dc { get; }
public IReadOnlyList<DcBus> Strings { get; }
public static AmptStatus Null => new AmptStatus(null, Array.Empty<DcBus>());
public required DcBus Dc { get; init; }
public required IReadOnlyList<DcBus> Strings { get; init; }
}
// public static AmptStatus Parallel(IReadOnlyList<AmptStatus> stati)
// {
// if (stati.Count == 0)
// {
// return new AmptStatus
// (
// Dc: DcBus.FromVoltageCurrent(0, 0),
// Strings: Array.Empty<DcBus>()
// );
// }
//
// var voltage = stati.Average(s => s.Dc.Voltage.Value);
// var current = stati.Sum(s => s.Dc.Current.Value);
// var dc = DcBus.FromVoltageCurrent(voltage, current);
//
// var strings = stati.SelectMany(s => s.Strings).ToList();
//
// return new AmptStatus(dc, strings);
// }

View File

@ -25,7 +25,5 @@ public class Battery48TlDevices
return Battery48TlRecords.Null;
}
}
}

View File

@ -16,7 +16,8 @@ public class DcDcDevicesRecord
public DcStatus Dc => new DcStatus
{
Battery = Devices.Count == 0 ? NoDevice
Battery = Devices.Count == 0
? NoDevice
: DcBus.FromVoltageCurrent
(
Devices.Average(r => r.Status.Dc.Battery.Voltage.Value),

View File

@ -1,5 +1,4 @@
using InnovEnergy.Lib.StatusApi.Connections;
using InnovEnergy.Lib.Units.Composite;
namespace InnovEnergy.Lib.StatusApi.DeviceTypes;