using System.Text.Json.Nodes; namespace InnovEnergy.Lib.StatusApi; /// SIGN CONVENTION /// /// Voltages have to be measured/indicated so that they are guaranteed to be never negative. /// In the case of AC this is accomplished by using the RMS measurement. /// The sign convention of the current (and hence power, since voltage defined to be never negative) /// depends on the type of the device. /// If the device can only produce (e.g. PV) or only consume (e.g. Loads), /// then the current has to be 0 or positive. /// If the device is a prosumer (e.g. inverter, battery, grid...) /// then a positive sign denotes current (power) flow away from the grid (to the "right") /// and a negative sign denotes current (power) flow towards the grid (to the "left") /// the currently known DeviceTypes, to be serialized as string in JSON public enum DeviceType { None, PvOnAcIn , PvOnAcOut , PvOnDc , Load , CriticalLoad, Battery , Grid , Inverter , AcInToAcOut , DcDc , DcLoad , Losses } public interface IJson { JsonNode ToJson(); } /// A phase must have at least a known Voltage and Current. /// For DC this is already enough. /// For AC the values have to be in RMS (not amplitude or P2P) /// Power can be inferred, P = UI public interface IPhase : IJson { public Double Voltage { get; } // U, non-negative public Double Current { get; } // I, sign depends on device type, see sign convention above } /// An AC phase additionally needs a field Phi denoting /// the phase difference between voltage and current /// Phi has to be in the interval [0,2pi) /// Apparent Power = U*I /// Active Power = cos(phi)*U*I /// Reactive Power = sin(phi)*U*I /// Power Factor = cos(phi) /// Active Power is signed (via cos(phi)) /// Current and Voltage are RMS and unsigned public interface IAcPhase : IPhase { public Double Phi { get; } } /// a device must have a Name and DeviceType public interface IDevice : IJson { DeviceType Type { get; } String? Name { get; } } /// A DC device must have a field denoting its DC connection public interface IDcDevice : IDevice { public IPhase Dc { get; } } /// An AC device can have 1 to 3 AC phases /// An AC device also needs a Frequency measurement /// Total power can be obtained by summing the power of the phases public interface IAcDevice : IDevice { public IAcPhase[] Ac { get; } // 1 to 3 phases public Double Frequency { get; } // non-negative } /// A low voltage 48V DC device /// Needed to distinguish the two sides of the DCDC /// Will be dropped once we get HV batteries public interface IDc48Device : IDevice { public IPhase? Dc48 { get; } } public interface IBattery : IJson { public Double Soc { get; } public Double Temperature { get; } } public interface IDc48Battery : IDc48Device, IBattery { } public interface IDcBattery : IDcDevice, IBattery { } /// An inverter has both an AC and a DC connection public interface IInverter : IAcDevice, IDcDevice { } public interface IDeviceStack : IJson { public IDevice[] Top { get; } public IDevice[] Right { get; } public IDevice[] Bottom { get; } public Boolean Disconnected { get; } } public interface IInstallationStatus: IJson { public IDeviceStack[] Stacks { get; } }