Initial commit
This commit is contained in:
@@ -0,0 +1,151 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Xylem.Common.CommonCore.Consts;
|
||||
using Xylem.Common.Hardware.Interfaces.Ports.PortCore.EventArguments;
|
||||
using Xylem.Common.Hardware.Interfaces.Ports.SerialPorts;
|
||||
using Xylem.Common.Hardware.WaterMeter.Genesis.Protocols.StreamingProtocol;
|
||||
|
||||
namespace Xylem.Common.Hardware.WaterMeter.Genesis.GenesisCore
|
||||
{
|
||||
public class GenesisMeterStreamingQuality : GenesisMeter
|
||||
{
|
||||
public QualityResult LastQualityResult;
|
||||
private StreamingDecoder sd;
|
||||
public Boolean IsRunning;
|
||||
private DateTimeOffset? _startTime;
|
||||
private DateTimeOffset? _stopTime;
|
||||
private List<String> _collectedRecords;
|
||||
private int? TillDecodedCount = null;
|
||||
public void StartStreamingQualityCheck(int? tillDecodedCount = null)
|
||||
{
|
||||
|
||||
if (IsRunning)
|
||||
{
|
||||
return;
|
||||
}
|
||||
TillDecodedCount = tillDecodedCount;
|
||||
if (TillDecodedCount.HasValue)
|
||||
{
|
||||
sd = new StreamingDecoder(false);
|
||||
}
|
||||
if (StreamingPort == null || !(StreamingPort is LedSerialPort))
|
||||
{
|
||||
throw new ApplicationException("No valid streaming port");
|
||||
}
|
||||
|
||||
_stopTime = null;
|
||||
_collectedRecords = new List<String>();
|
||||
|
||||
SyncStreamingBuffer(SyncMarkRecord.FlushBuffer);
|
||||
SyncStreamingBuffer(SyncMarkRecord.DecodeEveryPackage);
|
||||
((LedSerialPort)StreamingPort).OnRawRecordReceived += GenesisMeterStreamingQuality_OnRawRecordReceived;
|
||||
_startTime = DateTimeOffset.UtcNow;
|
||||
LogRawData(true);
|
||||
IsRunning = true;
|
||||
}
|
||||
|
||||
private void GenesisMeterStreamingQuality_OnRawRecordReceived(Object sender, BasePortDataEventArgs e)
|
||||
{
|
||||
_collectedRecords.Add(e.GetData().ToString());
|
||||
if (TillDecodedCount.HasValue)
|
||||
{
|
||||
if (sd.DecodeMsg(e.GetData().ToString()))
|
||||
{
|
||||
TillDecodedCount = TillDecodedCount.Value - 1;
|
||||
if (TillDecodedCount <= 0)
|
||||
{
|
||||
IsRunning = false;
|
||||
LastQualityResult = StopStreamingQualityCheck(10);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
public QualityResult StopStreamingQualityCheck(Int32 sampleRateHz)
|
||||
{
|
||||
_stopTime = DateTimeOffset.UtcNow;
|
||||
|
||||
if (!IsRunning && !_startTime.HasValue)
|
||||
{
|
||||
return new QualityResult();
|
||||
}
|
||||
|
||||
if (StreamingPort == null || !(StreamingPort is LedSerialPort))
|
||||
{
|
||||
throw new ApplicationException("No valid streaming port");
|
||||
}
|
||||
LogRawData(false);
|
||||
((LedSerialPort)StreamingPort).OnRawRecordReceived -= GenesisMeterStreamingQuality_OnRawRecordReceived;
|
||||
SyncStreamingBuffer(SyncMarkRecord.SkipDecoding);
|
||||
IsRunning = false;
|
||||
return new QualityResult(_collectedRecords, _stopTime.Value - _startTime.Value, sampleRateHz);
|
||||
}
|
||||
|
||||
public class QualityResult
|
||||
{
|
||||
public readonly Int32 TotalLinesCount;
|
||||
public readonly Int32 TotalDecodedCount;
|
||||
public readonly Int32 TotalTransportErrorCount;
|
||||
public readonly Int32 TotalValidationWithoutErrorsCount;
|
||||
public readonly Int32 ExpectedLinesCount;
|
||||
public readonly TimeSpan TotalTime;
|
||||
public readonly Dictionary<UInt16, Int32> ErrorOccurredCounter;
|
||||
|
||||
public QualityResult(List<String> collectedRecords, TimeSpan ts, Int32 sampleRateHz)
|
||||
{
|
||||
TotalLinesCount = collectedRecords.Count;
|
||||
TotalTime = ts;
|
||||
ExpectedLinesCount = (Int32)(Math.Round( ts.TotalSeconds * sampleRateHz, 0));
|
||||
ErrorOccurredCounter = new Dictionary<UInt16, Int32>();
|
||||
foreach (var rawText in collectedRecords)
|
||||
{
|
||||
var sd = new StreamingDecoder(false);
|
||||
if (!sd.DecodeMsg(rawText))
|
||||
{
|
||||
TotalTransportErrorCount++;
|
||||
continue;
|
||||
}
|
||||
//here the decoding is valid including the CRC
|
||||
TotalDecodedCount++;
|
||||
|
||||
//the DecodeMsg has assigned either a DataCalib or DataFlowTest data set
|
||||
var calibrationRecord = sd.DataCalib;
|
||||
var flowTestRecord = sd.DataFlowTest;
|
||||
|
||||
if (flowTestRecord != null)
|
||||
{
|
||||
TotalValidationWithoutErrorsCount++;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (calibrationRecord != null)
|
||||
{
|
||||
if (calibrationRecord.Validation == 0)
|
||||
{
|
||||
TotalValidationWithoutErrorsCount++;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (ErrorOccurredCounter.ContainsKey(calibrationRecord.Validation))
|
||||
{
|
||||
ErrorOccurredCounter[calibrationRecord.Validation] += 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
ErrorOccurredCounter.Add(calibrationRecord.Validation, 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public QualityResult()
|
||||
{
|
||||
TotalLinesCount = 0;
|
||||
TotalTime = TimeSpan.Zero;
|
||||
ErrorOccurredCounter = new Dictionary<UInt16, Int32>();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user