using System.Collections.Immutable; using InnovEnergy.Lib.Victron.VeDBus; using InnovEnergy.WireFormat.VictronV1; namespace InnovEnergy.VenusLogger.Parsers; using Props = ImmutableDictionary; public static class Utils { public static Phase ZeroPhase { get; } = new Phase { Current = 0, Voltage = 0 }; public static IEnumerable AcPhases { get; } = new[] { 1, 2, 3 }; public static IEnumerable ZeroPhases { get; } = new[] { ZeroPhase, ZeroPhase, ZeroPhase }; public static T? TryGetProperty(this Props props, String path, T? defaultValue = default(T?)) { try { return props.GetProperty(path); } catch { return defaultValue; } } // TODO: maybegetproperty? public static T GetProperty(this Props props, String path) { if (typeof(T).IsEnum) { var type = Enum.GetUnderlyingType(typeof(T)); var value = props.GetProperty(path, type); return (T) Enum.ToObject(typeof(T), value); } else { return (T) props.GetProperty(path, typeof(T)); } } private static Object GetProperty(this Props props, String path, Type type) { var value = props[path].Value; var isConvertible = type.GetInterface(nameof(IConvertible)) is not null; return isConvertible ? Convert.ChangeType(value, type) : value; } public static IEnumerable GetAcPhases(this Props props) { return AcPhases.TrySelect(props.ParseAcPhase); } public static Phase ParseAcPhase(this Props props, Int32 phase) => new Phase { Current = props.GetProperty($"/Ac/L{phase}/Current"), Voltage = props.GetProperty($"/Ac/L{phase}/Voltage"), Power = props.GetProperty($"/Ac/L{phase}/Power"), }; public static Phase GetDcPhase(this Props props, Int32 phase = 0) { var current = props.GetProperty($"/Dc/{phase}/Current"); var voltage = props.GetProperty($"/Dc/{phase}/Voltage"); var power = current * voltage; // if (props.ContainsKey($"/Dc/{phase}/Power")) // { // var losses = props.GetProperty($"/Dc/{phase}/Power") - power; // Console.WriteLine("Losses: " + losses); // } return new Phase { Current = current, Voltage = voltage, Power = power }; } }