Compare commits
3 Commits
26b7aa7e8b
...
38d28599ad
| Author | SHA1 | Date | |
|---|---|---|---|
| 38d28599ad | |||
| c9a4b0f3ce | |||
| b74f1fd644 |
39
TBF/Rig/Output/DB/ResultsWriter/Factory.cs
Normal file
39
TBF/Rig/Output/DB/ResultsWriter/Factory.cs
Normal file
@ -0,0 +1,39 @@
|
||||
///
|
||||
/// Copyright (c) 2026 Sensus Slovensko a.s.
|
||||
///
|
||||
|
||||
using System.Collections.Generic;
|
||||
using TBF.Rig.Generic;
|
||||
|
||||
namespace TBF.Rig.Output.DB.ResultsWriter
|
||||
{
|
||||
/// <summary>
|
||||
/// Factory component 'ResultsWriter'.
|
||||
/// Writes selected result items to database using parent UniDataStorageWriter.
|
||||
/// </summary>
|
||||
public class Factory : IComponentFactory
|
||||
{
|
||||
public string ClassName { get { return GetType().Namespace.Substring(8); } }
|
||||
public override string ToString() { return ClassName; }
|
||||
|
||||
public IComponent DummyComponent()
|
||||
{
|
||||
return new ResultsWriter();
|
||||
}
|
||||
|
||||
public IComponent GetComponent(IComponentCfg cfg, IList<IComponent> components)
|
||||
{
|
||||
return new ResultsWriter(cfg, components);
|
||||
}
|
||||
|
||||
public IComponentCfg DefaultConfig()
|
||||
{
|
||||
return new ResultsWriterCfg("ResultsWriter", this);
|
||||
}
|
||||
|
||||
public IComponentCfg CmpntCfgFromCmpntEntity(Config.Entities.Component component)
|
||||
{
|
||||
return ComponentCfgBase.CreateFromDbEntity(ResultsWriterCfg.Serializer, component, this);
|
||||
}
|
||||
}
|
||||
}
|
||||
281
TBF/Rig/Output/DB/ResultsWriter/ResultsWriter.cs
Normal file
281
TBF/Rig/Output/DB/ResultsWriter/ResultsWriter.cs
Normal file
@ -0,0 +1,281 @@
|
||||
///
|
||||
/// Copyright (c) 2026 Sensus Slovensko a.s.
|
||||
///
|
||||
|
||||
using Common;
|
||||
using log4net;
|
||||
using Results.Entities;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using TBF.Rig.Generic;
|
||||
using TBF.Rig.Output.DataStorage.UniDataStorageWriter;
|
||||
using TBF.Rig.Output.DataStorage.UniDataStorageWriter.Interfaces;
|
||||
using TBF.Rig.Sequences;
|
||||
|
||||
namespace TBF.Rig.Output.DB.ResultsWriter
|
||||
{
|
||||
public class ResultsWriter : ComponentBase, IOperation, GenericDevices.IResultsWriter, Generic.IDevice
|
||||
{
|
||||
private static readonly ILog log = LogManager.GetLogger(typeof(ResultsWriter));
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return string.Format("{0}({1})", ClassName, Cfg.ToString(-1));
|
||||
}
|
||||
|
||||
ResultsWriterCfg resultsWriterCfg;
|
||||
|
||||
Batch batch;
|
||||
|
||||
bool opCompleted;
|
||||
bool anyError;
|
||||
|
||||
enum OpState
|
||||
{
|
||||
None,
|
||||
WriteResultsScheduled,
|
||||
WriteResultsRunning,
|
||||
}
|
||||
|
||||
OpState currentOpState;
|
||||
|
||||
TBF.Rig.Output.DataStorage.UniDataStorageWriter.Writer dataStorageWriter;
|
||||
|
||||
public ResultsWriter()
|
||||
{
|
||||
}
|
||||
|
||||
public ResultsWriter(IComponentCfg cfg, IList<IComponent> components) : base(cfg)
|
||||
{
|
||||
resultsWriterCfg = cfg as ResultsWriterCfg;
|
||||
if (resultsWriterCfg == null)
|
||||
throw new ArgumentException("resultsWriterCfg");
|
||||
|
||||
currentOpState = OpState.None;
|
||||
|
||||
log.Warn(this.ToString());
|
||||
|
||||
IComponent parent =
|
||||
components.FirstOrDefault(c => c.Name == resultsWriterCfg.ParentName);
|
||||
|
||||
if (parent == null)
|
||||
{
|
||||
throw new Exception(
|
||||
string.Format("Parent '{0}' was not found.",
|
||||
resultsWriterCfg.ParentName));
|
||||
}
|
||||
|
||||
log.WarnFormat(
|
||||
"ResultsWriter parent found: Name={0}, Type={1}",
|
||||
parent.Name,
|
||||
parent.GetType().FullName);
|
||||
|
||||
dataStorageWriter = parent as TBF.Rig.Output.DataStorage.UniDataStorageWriter.Writer;
|
||||
|
||||
if (dataStorageWriter == null)
|
||||
{
|
||||
throw new Exception(
|
||||
string.Format(
|
||||
"Parent '{0}' of type '{1}' is not UniDataStorageWriter.Writer.",
|
||||
resultsWriterCfg.ParentName,
|
||||
parent.GetType().FullName));
|
||||
}
|
||||
}
|
||||
|
||||
public ResultsWriter(IComponentCfg cfg) : base(cfg)
|
||||
{
|
||||
resultsWriterCfg = cfg as ResultsWriterCfg;
|
||||
if (resultsWriterCfg == null)
|
||||
throw new ArgumentException("resultsWriterCfg");
|
||||
|
||||
currentOpState = OpState.None;
|
||||
|
||||
log.Warn(this.ToString());
|
||||
}
|
||||
|
||||
///
|
||||
/// IDevice interface implementation
|
||||
///
|
||||
public override void Initialize()
|
||||
{
|
||||
}
|
||||
|
||||
public void RunDeviceBefore()
|
||||
{
|
||||
}
|
||||
|
||||
public void RunDeviceAfter()
|
||||
{
|
||||
}
|
||||
|
||||
public void StopDevice()
|
||||
{
|
||||
}
|
||||
|
||||
public void StopDevice2()
|
||||
{
|
||||
}
|
||||
|
||||
///
|
||||
/// GenericDevices.IResultsWriter
|
||||
///
|
||||
public IOperation ProcessResultsOp(Batch batch)
|
||||
{
|
||||
if (!resultsWriterCfg.Enabled)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
if (currentOpState == OpState.WriteResultsRunning)
|
||||
{
|
||||
throw new Exception("Sequence error");
|
||||
}
|
||||
|
||||
this.batch = batch;
|
||||
currentOpState = OpState.WriteResultsScheduled;
|
||||
return this;
|
||||
}
|
||||
|
||||
///
|
||||
/// IOperation
|
||||
///
|
||||
public void Start()
|
||||
{
|
||||
if (currentOpState == OpState.WriteResultsScheduled)
|
||||
{
|
||||
currentOpState = OpState.WriteResultsRunning;
|
||||
}
|
||||
|
||||
opCompleted = false;
|
||||
anyError = false;
|
||||
}
|
||||
|
||||
public Event Run()
|
||||
{
|
||||
log.WarnFormat("{0} : Run() : currentOp = {1}", Name, currentOpState);
|
||||
|
||||
if (currentOpState == OpState.WriteResultsRunning)
|
||||
{
|
||||
if (resultsWriterCfg.DebugLevel == DebugMode.Simulate)
|
||||
{
|
||||
return Event.ResultsWritten;
|
||||
}
|
||||
|
||||
if (batch == null || batch.WaterMeters == null || batch.WaterMeters.Count == 0)
|
||||
{
|
||||
return Event.ResultsWritten;
|
||||
}
|
||||
|
||||
if (opCompleted)
|
||||
{
|
||||
return anyError ? Event.ErrorProcessingResults : Event.ResultsWritten;
|
||||
}
|
||||
|
||||
opCompleted = true;
|
||||
|
||||
try
|
||||
{
|
||||
WriteBatchResults(batch);
|
||||
}
|
||||
catch (Exception exc)
|
||||
{
|
||||
anyError = true;
|
||||
log.ErrorFormat("Failed to write results by ResultsWriter: {0}", exc);
|
||||
}
|
||||
|
||||
return anyError ? Event.ErrorProcessingResults : Event.ResultsWritten;
|
||||
}
|
||||
|
||||
return Event.None;
|
||||
}
|
||||
|
||||
public void Stop()
|
||||
{
|
||||
currentOpState = OpState.None;
|
||||
}
|
||||
|
||||
public void WriteBatchResults(Batch batch)
|
||||
{
|
||||
resultsWriterCfg.UpdateRuntimeModel();
|
||||
|
||||
foreach (var wm in batch.WaterMeters)
|
||||
{
|
||||
if (wm == null || wm.Disabled)
|
||||
continue;
|
||||
|
||||
DataWriteRequest request = BuildWriteRequest(wm);
|
||||
|
||||
if (request.InsertItems.Count == 0)
|
||||
{
|
||||
log.WarnFormat("No values to write for WM position {0}", wm.WMPosition);
|
||||
continue;
|
||||
}
|
||||
|
||||
log.InfoFormat("Writing WMPosition={0}, SerialNr={1}", wm.WMPosition, wm.SerialNr);
|
||||
|
||||
var result = dataStorageWriter.SetData(request);
|
||||
|
||||
if (!result.Success)
|
||||
{
|
||||
throw new Exception(result.Message);
|
||||
}
|
||||
|
||||
log.WarnFormat(
|
||||
"ResultsWriter wrote {0} value(s) for WM position {1}",
|
||||
request.InsertItems.Count,
|
||||
wm.WMPosition);
|
||||
}
|
||||
}
|
||||
|
||||
DataWriteRequest BuildWriteRequest(WaterMeter wm)
|
||||
{
|
||||
var request = new DataWriteRequest();
|
||||
request.Mode = WriteMode.Insert;
|
||||
|
||||
if (resultsWriterCfg.SelectedItems == null)
|
||||
return request;
|
||||
|
||||
foreach (var item in resultsWriterCfg.SelectedItems)
|
||||
{
|
||||
if (item == null)
|
||||
continue;
|
||||
|
||||
string columnName = item.Caption;
|
||||
|
||||
if (string.IsNullOrWhiteSpace(columnName))
|
||||
{
|
||||
log.WarnFormat("Result item with empty Caption skipped: {0}", item);
|
||||
continue;
|
||||
}
|
||||
|
||||
request.InsertItems.Add(new InsertWriteItem()
|
||||
{
|
||||
ColumnName = columnName,
|
||||
Value = item.Print(wm)
|
||||
});
|
||||
}
|
||||
|
||||
return request;
|
||||
}
|
||||
|
||||
public void InitializeParent()
|
||||
{
|
||||
IComponent parent = TbfComponents.FindComponent(resultsWriterCfg.ParentName);
|
||||
|
||||
if (parent == null)
|
||||
throw new Exception(
|
||||
string.Format("Parent '{0}' was not found.", resultsWriterCfg.ParentName));
|
||||
|
||||
dataStorageWriter =
|
||||
parent as TBF.Rig.Output.DataStorage.UniDataStorageWriter.Writer;
|
||||
|
||||
if (dataStorageWriter == null)
|
||||
throw new Exception(
|
||||
string.Format(
|
||||
"Parent '{0}' of type '{1}' is not UniDataStorageWriter.Writer.",
|
||||
resultsWriterCfg.ParentName,
|
||||
parent.GetType().FullName));
|
||||
}
|
||||
}
|
||||
}
|
||||
88
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterCfg.cs
Normal file
88
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterCfg.cs
Normal file
@ -0,0 +1,88 @@
|
||||
///
|
||||
/// Copyright (c) 2026 Sensus Slovensko a.s.
|
||||
///
|
||||
|
||||
using System.Collections.Generic;
|
||||
using System.Xml.Serialization;
|
||||
using Results;
|
||||
using TBF.Rig.Generic;
|
||||
|
||||
namespace TBF.Rig.Output.DB.ResultsWriter
|
||||
{
|
||||
public class ResultsWriterCfg : ComponentCfgBase, IComponentCfg
|
||||
{
|
||||
public static XmlSerializer Serializer =
|
||||
XmlSerializer.FromTypes(new[] { typeof(ResultsWriterCfg) })[0];
|
||||
|
||||
public override XmlSerializer GetSerializer()
|
||||
{
|
||||
return Serializer;
|
||||
}
|
||||
|
||||
public IComponentCfgCtrl GetControl(IList<Config.Entities.Component> cmpntEntities)
|
||||
{
|
||||
return new ResultsWriterCfgCtrl(cmpntEntities);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Enables or disables writing.
|
||||
/// </summary>
|
||||
public bool Enabled;
|
||||
|
||||
/// <summary>
|
||||
/// Target table or logical storage name for UniDataStorageWriter.
|
||||
/// </summary>
|
||||
public string StorageName;
|
||||
|
||||
/// Runtime model used ResultsConfigCtrl
|
||||
[XmlIgnore]
|
||||
public List<WMeterRsltItemSpec> SelectedItems;
|
||||
|
||||
public string[] Items;
|
||||
|
||||
/// Serializable model
|
||||
public List<ResultsWriterItemCfg> SelectedItemsCfg;
|
||||
|
||||
ResultsWriterCfg()
|
||||
{
|
||||
ParentName = string.Empty; // here should be UniDataStorageWriter component name
|
||||
SelectedItems = new List<WMeterRsltItemSpec>();
|
||||
SelectedItemsCfg = new List<ResultsWriterItemCfg>();
|
||||
Enabled = true;
|
||||
StorageName = "Results";
|
||||
}
|
||||
|
||||
public ResultsWriterCfg(string name, IComponentFactory factory)
|
||||
: this()
|
||||
{
|
||||
Name = name;
|
||||
Factory = factory;
|
||||
}
|
||||
|
||||
public string ToString(int i)
|
||||
{
|
||||
return string.Format(
|
||||
"Name={0}, Parent={1}, Enabled={2}, StorageName={3}, Items={4}",
|
||||
Name,
|
||||
ParentName,
|
||||
Enabled,
|
||||
StorageName,
|
||||
SelectedItems != null ? SelectedItems.Count : 0);
|
||||
}
|
||||
|
||||
public void UpdateSerializableModel()
|
||||
{
|
||||
Items = WMeterRsltItemSpec.ToStrArray(SelectedItems);
|
||||
}
|
||||
|
||||
public void UpdateRuntimeModel()
|
||||
{
|
||||
SelectedItems = new List<WMeterRsltItemSpec>();
|
||||
|
||||
if (Items == null)
|
||||
return;
|
||||
|
||||
SelectedItems.AddRange(WMeterRsltItemSpec.FromStrArray(Items));
|
||||
}
|
||||
}
|
||||
}
|
||||
142
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterCfgCtrl.Designer.cs
generated
Normal file
142
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterCfgCtrl.Designer.cs
generated
Normal file
@ -0,0 +1,142 @@
|
||||
namespace TBF.Rig.Output.DB.ResultsWriter
|
||||
{
|
||||
partial class ResultsWriterCfgCtrl
|
||||
{
|
||||
private System.ComponentModel.IContainer components = null;
|
||||
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
if (disposing && (components != null)) components.Dispose();
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
private void InitializeComponent()
|
||||
{
|
||||
this.classNameLabel = new System.Windows.Forms.Label();
|
||||
this.nameTextBox = new System.Windows.Forms.TextBox();
|
||||
this.nameLabel = new System.Windows.Forms.Label();
|
||||
this.parentLabel = new System.Windows.Forms.Label();
|
||||
this.parentComboBox = new System.Windows.Forms.ComboBox();
|
||||
this.enabledCheckBox = new System.Windows.Forms.CheckBox();
|
||||
this.storageNameLabel = new System.Windows.Forms.Label();
|
||||
this.storageNameTextBox = new System.Windows.Forms.TextBox();
|
||||
this.configureResultsButton = new System.Windows.Forms.Button();
|
||||
this.selectedItemsLabel = new System.Windows.Forms.Label();
|
||||
this.previewRequestButton = new System.Windows.Forms.Button();
|
||||
this.SuspendLayout();
|
||||
|
||||
this.previewRequestButton.Enabled = false;
|
||||
this.previewRequestButton.Location = new System.Drawing.Point(150, 204);
|
||||
this.previewRequestButton.Name = "previewRequestButton";
|
||||
this.previewRequestButton.Size = new System.Drawing.Size(160, 30);
|
||||
this.previewRequestButton.TabIndex = 10;
|
||||
this.previewRequestButton.Text = "Preview request...";
|
||||
this.previewRequestButton.UseVisualStyleBackColor = true;
|
||||
this.previewRequestButton.Click += new System.EventHandler(this.previewRequestButton_Click);
|
||||
|
||||
this.classNameLabel.AutoSize = true;
|
||||
this.classNameLabel.Location = new System.Drawing.Point(14, 12);
|
||||
this.classNameLabel.Name = "classNameLabel";
|
||||
this.classNameLabel.Size = new System.Drawing.Size(75, 13);
|
||||
this.classNameLabel.TabIndex = 0;
|
||||
this.classNameLabel.Text = "ResultsWriter";
|
||||
|
||||
this.nameLabel.AutoSize = true;
|
||||
this.nameLabel.Location = new System.Drawing.Point(14, 45);
|
||||
this.nameLabel.Name = "nameLabel";
|
||||
this.nameLabel.Size = new System.Drawing.Size(38, 13);
|
||||
this.nameLabel.TabIndex = 1;
|
||||
this.nameLabel.Text = "Name:";
|
||||
|
||||
this.nameTextBox.Enabled = false;
|
||||
this.nameTextBox.Location = new System.Drawing.Point(150, 42);
|
||||
this.nameTextBox.Name = "nameTextBox";
|
||||
this.nameTextBox.Size = new System.Drawing.Size(260, 20);
|
||||
this.nameTextBox.TabIndex = 2;
|
||||
|
||||
this.parentLabel.AutoSize = true;
|
||||
this.parentLabel.Location = new System.Drawing.Point(14, 75);
|
||||
this.parentLabel.Name = "parentLabel";
|
||||
this.parentLabel.Size = new System.Drawing.Size(123, 13);
|
||||
this.parentLabel.TabIndex = 3;
|
||||
this.parentLabel.Text = "UniDataStorageWriter:";
|
||||
|
||||
this.parentComboBox.Enabled = false;
|
||||
this.parentComboBox.DropDownStyle = System.Windows.Forms.ComboBoxStyle.DropDownList;
|
||||
this.parentComboBox.FormattingEnabled = true;
|
||||
this.parentComboBox.Location = new System.Drawing.Point(150, 72);
|
||||
this.parentComboBox.Name = "parentComboBox";
|
||||
this.parentComboBox.Size = new System.Drawing.Size(260, 21);
|
||||
this.parentComboBox.TabIndex = 4;
|
||||
|
||||
this.enabledCheckBox.AutoSize = true;
|
||||
this.enabledCheckBox.Enabled = false;
|
||||
this.enabledCheckBox.Location = new System.Drawing.Point(150, 103);
|
||||
this.enabledCheckBox.Name = "enabledCheckBox";
|
||||
this.enabledCheckBox.Size = new System.Drawing.Size(65, 17);
|
||||
this.enabledCheckBox.TabIndex = 5;
|
||||
this.enabledCheckBox.Text = "Enabled";
|
||||
this.enabledCheckBox.UseVisualStyleBackColor = true;
|
||||
|
||||
this.storageNameLabel.AutoSize = true;
|
||||
this.storageNameLabel.Location = new System.Drawing.Point(14, 133);
|
||||
this.storageNameLabel.Name = "storageNameLabel";
|
||||
this.storageNameLabel.Size = new System.Drawing.Size(77, 13);
|
||||
this.storageNameLabel.TabIndex = 6;
|
||||
this.storageNameLabel.Text = "Storage name:";
|
||||
|
||||
this.storageNameTextBox.Enabled = false;
|
||||
this.storageNameTextBox.Location = new System.Drawing.Point(150, 130);
|
||||
this.storageNameTextBox.Name = "storageNameTextBox";
|
||||
this.storageNameTextBox.Size = new System.Drawing.Size(260, 20);
|
||||
this.storageNameTextBox.TabIndex = 7;
|
||||
|
||||
this.configureResultsButton.Enabled = false;
|
||||
this.configureResultsButton.Location = new System.Drawing.Point(150, 168);
|
||||
this.configureResultsButton.Name = "configureResultsButton";
|
||||
this.configureResultsButton.Size = new System.Drawing.Size(160, 30);
|
||||
this.configureResultsButton.TabIndex = 8;
|
||||
this.configureResultsButton.Text = "Configure results...";
|
||||
this.configureResultsButton.UseVisualStyleBackColor = true;
|
||||
this.configureResultsButton.Click += new System.EventHandler(this.configureResultsButton_Click);
|
||||
|
||||
this.selectedItemsLabel.AutoSize = true;
|
||||
this.selectedItemsLabel.Location = new System.Drawing.Point(325, 176);
|
||||
this.selectedItemsLabel.Name = "selectedItemsLabel";
|
||||
this.selectedItemsLabel.Size = new System.Drawing.Size(92, 13);
|
||||
this.selectedItemsLabel.TabIndex = 9;
|
||||
this.selectedItemsLabel.Text = "0 selected item(s)";
|
||||
|
||||
this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
|
||||
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
||||
this.Controls.Add(this.selectedItemsLabel);
|
||||
this.Controls.Add(this.configureResultsButton);
|
||||
this.Controls.Add(this.storageNameTextBox);
|
||||
this.Controls.Add(this.storageNameLabel);
|
||||
this.Controls.Add(this.enabledCheckBox);
|
||||
this.Controls.Add(this.parentComboBox);
|
||||
this.Controls.Add(this.parentLabel);
|
||||
this.Controls.Add(this.nameTextBox);
|
||||
this.Controls.Add(this.nameLabel);
|
||||
this.Controls.Add(this.classNameLabel);
|
||||
this.Controls.Add(this.previewRequestButton);
|
||||
this.Name = "ResultsWriterCfgCtrl";
|
||||
this.Size = new System.Drawing.Size(620, 260);
|
||||
this.Load += new System.EventHandler(this.ResultsWriterCfgCtrl_Load);
|
||||
this.ResumeLayout(false);
|
||||
this.PerformLayout();
|
||||
}
|
||||
|
||||
private System.Windows.Forms.Label classNameLabel;
|
||||
private System.Windows.Forms.TextBox nameTextBox;
|
||||
private System.Windows.Forms.Label nameLabel;
|
||||
private System.Windows.Forms.Label parentLabel;
|
||||
private System.Windows.Forms.ComboBox parentComboBox;
|
||||
private System.Windows.Forms.CheckBox enabledCheckBox;
|
||||
private System.Windows.Forms.Label storageNameLabel;
|
||||
private System.Windows.Forms.TextBox storageNameTextBox;
|
||||
private System.Windows.Forms.Button configureResultsButton;
|
||||
private System.Windows.Forms.Label selectedItemsLabel;
|
||||
private System.Windows.Forms.Button previewRequestButton;
|
||||
}
|
||||
}
|
||||
243
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterCfgCtrl.cs
Normal file
243
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterCfgCtrl.cs
Normal file
@ -0,0 +1,243 @@
|
||||
///
|
||||
/// Copyright (c) 2026 Sensus Slovensko a.s.
|
||||
///
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Windows.Forms;
|
||||
using Common;
|
||||
using Config.Entities;
|
||||
using TBF.Rig.Generic;
|
||||
|
||||
namespace TBF.Rig.Output.DB.ResultsWriter
|
||||
{
|
||||
public partial class ResultsWriterCfgCtrl : Configs.ConfigCtrlUtils, IComponentCfgCtrl
|
||||
{
|
||||
public bool ShowMore { get { return false; } }
|
||||
|
||||
ResultsWriterCfg config;
|
||||
IList<Component> cmpntEntities;
|
||||
|
||||
bool resultsConfigChanged;
|
||||
|
||||
public IComponentCfg Config
|
||||
{
|
||||
get { return config as IComponentCfg; }
|
||||
set
|
||||
{
|
||||
config = value as ResultsWriterCfg;
|
||||
Redraw();
|
||||
}
|
||||
}
|
||||
|
||||
public ResultsWriterCfgCtrl(IList<Component> cmpntEntities)
|
||||
{
|
||||
InitializeComponent();
|
||||
this.cmpntEntities = cmpntEntities;
|
||||
}
|
||||
|
||||
private void ResultsWriterCfgCtrl_Load(object sender, EventArgs e)
|
||||
{
|
||||
if (config == null) return;
|
||||
Redraw();
|
||||
}
|
||||
|
||||
public void Closing()
|
||||
{
|
||||
}
|
||||
|
||||
void Redraw()
|
||||
{
|
||||
if (config == null) return;
|
||||
|
||||
config.UpdateRuntimeModel();
|
||||
|
||||
classNameLabel.Text = config.Factory.ClassName;
|
||||
nameTextBox.Text = config.Name;
|
||||
enabledCheckBox.Checked = config.Enabled;
|
||||
storageNameTextBox.Text = config.StorageName;
|
||||
|
||||
parentComboBox.Items.Clear();
|
||||
parentComboBox.Items.Add(string.Empty);
|
||||
|
||||
if (cmpntEntities != null)
|
||||
{
|
||||
foreach (Component cmpnt in cmpntEntities)
|
||||
{
|
||||
if (cmpnt == null) continue;
|
||||
|
||||
// for now, a simple filter by name/classname
|
||||
if (cmpnt.ClassName != null &&
|
||||
cmpnt.ClassName.IndexOf("UniDataStorageWriter") >= 0)
|
||||
{
|
||||
parentComboBox.Items.Add(cmpnt.Name);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
parentComboBox.Text = config.ParentName;
|
||||
|
||||
selectedItemsLabel.Text = string.Format(
|
||||
"{0} selected item(s)",
|
||||
config.SelectedItems != null ? config.SelectedItems.Count : 0);
|
||||
|
||||
resultsConfigChanged = false;
|
||||
}
|
||||
|
||||
public void Unlock()
|
||||
{
|
||||
nameTextBox.Enabled = true;
|
||||
enabledCheckBox.Enabled = true;
|
||||
parentComboBox.Enabled = true;
|
||||
storageNameTextBox.Enabled = true;
|
||||
configureResultsButton.Enabled = true;
|
||||
previewRequestButton.Enabled = true;
|
||||
}
|
||||
|
||||
public CfgUpdateFlags VerifyCfg(ref string message)
|
||||
{
|
||||
if (string.IsNullOrEmpty(nameTextBox.Text))
|
||||
{
|
||||
message = "Component name is empty.";
|
||||
return CfgUpdateFlags.Error;
|
||||
}
|
||||
|
||||
if (enabledCheckBox.Checked && string.IsNullOrEmpty(parentComboBox.Text))
|
||||
{
|
||||
message = "Parent UniDataStorageWriter is not selected.";
|
||||
return CfgUpdateFlags.Error;
|
||||
}
|
||||
|
||||
if (enabledCheckBox.Checked && string.IsNullOrEmpty(storageNameTextBox.Text))
|
||||
{
|
||||
message = "Storage name is empty.";
|
||||
return CfgUpdateFlags.Error;
|
||||
}
|
||||
|
||||
return CfgUpdateFlags.None;
|
||||
}
|
||||
|
||||
public CfgUpdateFlags UpdateCfg()
|
||||
{
|
||||
CfgUpdateFlags flags = CfgUpdateFlags.None;
|
||||
|
||||
if (config == null) return CfgUpdateFlags.Error;
|
||||
|
||||
if (config.Name != nameTextBox.Text)
|
||||
{
|
||||
config.Name = nameTextBox.Text;
|
||||
flags |= CfgUpdateFlags.AnyChange | CfgUpdateFlags.RestartRqrd;
|
||||
}
|
||||
|
||||
if (config.ParentName != parentComboBox.Text)
|
||||
{
|
||||
config.ParentName = parentComboBox.Text;
|
||||
flags |= CfgUpdateFlags.AnyChange | CfgUpdateFlags.RestartRqrd;
|
||||
}
|
||||
|
||||
flags |= UpdateDifferent(
|
||||
ref config.Enabled,
|
||||
enabledCheckBox.Checked,
|
||||
CfgUpdateFlags.AnyChange | CfgUpdateFlags.RestartRqrd);
|
||||
|
||||
flags |= UpdateDifferent(
|
||||
ref config.StorageName,
|
||||
storageNameTextBox.Text,
|
||||
CfgUpdateFlags.AnyChange | CfgUpdateFlags.RestartRqrd);
|
||||
|
||||
if (resultsConfigChanged)
|
||||
{
|
||||
flags |= CfgUpdateFlags.AnyChange | CfgUpdateFlags.RestartRqrd;
|
||||
resultsConfigChanged = false;
|
||||
}
|
||||
|
||||
return flags;
|
||||
}
|
||||
|
||||
private void configureResultsButton_Click(object sender, EventArgs e)
|
||||
{
|
||||
if (config == null) return;
|
||||
|
||||
using (ResultsWriterResultsDlg dlg = new ResultsWriterResultsDlg())
|
||||
{
|
||||
dlg.SelectedItems = config.SelectedItems;
|
||||
|
||||
if (dlg.ShowDialog(this) == DialogResult.OK)
|
||||
{
|
||||
config.SelectedItems = new List<Results.WMeterRsltItemSpec>(dlg.SelectedItems);
|
||||
config.UpdateSerializableModel();
|
||||
resultsConfigChanged = true;
|
||||
|
||||
selectedItemsLabel.Text = string.Format(
|
||||
"{0} selected item(s)",
|
||||
config.SelectedItems != null ? config.SelectedItems.Count : 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void previewRequestButton_Click(object sender, EventArgs e)
|
||||
{
|
||||
if (config == null) return;
|
||||
|
||||
Results.Entities.Batch batch = CreateSimulationBatch();
|
||||
|
||||
if (batch == null || batch.WaterMeters == null || batch.WaterMeters.Count == 0)
|
||||
{
|
||||
MessageBox.Show(
|
||||
"No current batch results are available.",
|
||||
"ResultsWriter",
|
||||
MessageBoxButtons.OK,
|
||||
MessageBoxIcon.Information);
|
||||
return;
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
config.UpdateRuntimeModel();
|
||||
|
||||
ResultsWriter writer = new ResultsWriter(config);
|
||||
writer.InitializeParent();
|
||||
writer.WriteBatchResults(batch);
|
||||
|
||||
MessageBox.Show(
|
||||
"Current batch was written by ResultsWriter.",
|
||||
"ResultsWriter",
|
||||
MessageBoxButtons.OK,
|
||||
MessageBoxIcon.Information);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
MessageBox.Show(
|
||||
ex.Message,
|
||||
"ResultsWriter write failed",
|
||||
MessageBoxButtons.OK,
|
||||
MessageBoxIcon.Error);
|
||||
}
|
||||
}
|
||||
|
||||
private Results.Entities.Batch CreateSimulationBatch()
|
||||
{
|
||||
Results.Entities.Batch batch = new Results.Entities.Batch();
|
||||
|
||||
batch.BatchNr = 999999;
|
||||
batch.ProcedureName = "ResultsWriter simulation";
|
||||
batch.StartTime = DateTime.Now;
|
||||
batch.EndTime = DateTime.Now;
|
||||
batch.TestBenchName = "Mexico";
|
||||
|
||||
Results.Entities.WaterMeter wm1 = new Results.Entities.WaterMeter();
|
||||
wm1.Batch = batch;
|
||||
wm1.WMPosition = 1;
|
||||
wm1.SerialNr = "SN000001";
|
||||
batch.WaterMeters.Add(wm1);
|
||||
|
||||
Results.Entities.WaterMeter wm2 = new Results.Entities.WaterMeter();
|
||||
wm2.Batch = batch;
|
||||
wm2.WMPosition = 2;
|
||||
wm2.SerialNr = "SN000002";
|
||||
batch.WaterMeters.Add(wm2);
|
||||
|
||||
return batch;
|
||||
}
|
||||
}
|
||||
}
|
||||
44
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterItemCfg.cs
Normal file
44
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterItemCfg.cs
Normal file
@ -0,0 +1,44 @@
|
||||
///
|
||||
/// Copyright (c) 2026 Sensus Slovensko a.s.
|
||||
///
|
||||
|
||||
namespace TBF.Rig.Output.DB.ResultsWriter
|
||||
{
|
||||
/// <summary>
|
||||
/// Serializable representation of one configured Results item.
|
||||
/// Source identifies the original TBF variable, Caption represents
|
||||
/// the destination database column name.
|
||||
/// </summary>
|
||||
public class ResultsWriterItemCfg
|
||||
{
|
||||
/// <summary>
|
||||
/// Original Results expression (for rebuilding the model).
|
||||
/// Example: "Conduct.ME()"
|
||||
/// </summary>
|
||||
public string Source;
|
||||
|
||||
/// <summary>
|
||||
/// Destination database column name.
|
||||
/// </summary>
|
||||
public string Caption;
|
||||
|
||||
public string Units;
|
||||
public string Format;
|
||||
|
||||
public int Precision;
|
||||
public int Width;
|
||||
|
||||
public string Alignment;
|
||||
public bool Merge;
|
||||
|
||||
public ResultsWriterItemCfg()
|
||||
{
|
||||
Source = string.Empty;
|
||||
Caption = string.Empty;
|
||||
Units = string.Empty;
|
||||
Format = string.Empty;
|
||||
Alignment = string.Empty;
|
||||
Merge = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
72
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterResultsDlg.Designer.cs
generated
Normal file
72
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterResultsDlg.Designer.cs
generated
Normal file
@ -0,0 +1,72 @@
|
||||
namespace TBF.Rig.Output.DB.ResultsWriter
|
||||
{
|
||||
partial class ResultsWriterResultsDlg
|
||||
{
|
||||
private System.ComponentModel.IContainer components = null;
|
||||
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
if (disposing && (components != null)) components.Dispose();
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
private void InitializeComponent()
|
||||
{
|
||||
this.resultsConfigCtrl = new Results.Forms.ResultsConfigCtrl();
|
||||
this.okButton = new System.Windows.Forms.Button();
|
||||
this.cancelButton = new System.Windows.Forms.Button();
|
||||
this.SuspendLayout();
|
||||
|
||||
this.resultsConfigCtrl.Anchor =
|
||||
((System.Windows.Forms.AnchorStyles)((((System.Windows.Forms.AnchorStyles.Top |
|
||||
System.Windows.Forms.AnchorStyles.Bottom) |
|
||||
System.Windows.Forms.AnchorStyles.Left) |
|
||||
System.Windows.Forms.AnchorStyles.Right)));
|
||||
this.resultsConfigCtrl.Location = new System.Drawing.Point(3, 3);
|
||||
this.resultsConfigCtrl.Name = "resultsConfigCtrl";
|
||||
this.resultsConfigCtrl.Size = new System.Drawing.Size(925, 496);
|
||||
this.resultsConfigCtrl.TabIndex = 0;
|
||||
this.resultsConfigCtrl.Unlocked = true;
|
||||
|
||||
this.okButton.Anchor =
|
||||
((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom |
|
||||
System.Windows.Forms.AnchorStyles.Right)));
|
||||
this.okButton.Location = new System.Drawing.Point(714, 512);
|
||||
this.okButton.Name = "okButton";
|
||||
this.okButton.Size = new System.Drawing.Size(104, 30);
|
||||
this.okButton.TabIndex = 1;
|
||||
this.okButton.Text = "OK";
|
||||
this.okButton.UseVisualStyleBackColor = true;
|
||||
this.okButton.Click += new System.EventHandler(this.okButton_Click);
|
||||
|
||||
this.cancelButton.Anchor =
|
||||
((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom |
|
||||
System.Windows.Forms.AnchorStyles.Right)));
|
||||
this.cancelButton.DialogResult = System.Windows.Forms.DialogResult.Cancel;
|
||||
this.cancelButton.Location = new System.Drawing.Point(824, 512);
|
||||
this.cancelButton.Name = "cancelButton";
|
||||
this.cancelButton.Size = new System.Drawing.Size(104, 30);
|
||||
this.cancelButton.TabIndex = 2;
|
||||
this.cancelButton.Text = "Cancel";
|
||||
this.cancelButton.UseVisualStyleBackColor = true;
|
||||
|
||||
this.AcceptButton = this.okButton;
|
||||
this.CancelButton = this.cancelButton;
|
||||
this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
|
||||
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
||||
this.ClientSize = new System.Drawing.Size(940, 554);
|
||||
this.Controls.Add(this.cancelButton);
|
||||
this.Controls.Add(this.okButton);
|
||||
this.Controls.Add(this.resultsConfigCtrl);
|
||||
this.Name = "ResultsWriterResultsDlg";
|
||||
this.StartPosition = System.Windows.Forms.FormStartPosition.CenterParent;
|
||||
this.Text = "ResultsWriter configuration";
|
||||
this.Load += new System.EventHandler(this.ResultsWriterResultsDlg_Load);
|
||||
this.ResumeLayout(false);
|
||||
}
|
||||
|
||||
private Results.Forms.ResultsConfigCtrl resultsConfigCtrl;
|
||||
private System.Windows.Forms.Button okButton;
|
||||
private System.Windows.Forms.Button cancelButton;
|
||||
}
|
||||
}
|
||||
45
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterResultsDlg.cs
Normal file
45
TBF/Rig/Output/DB/ResultsWriter/ResultsWriterResultsDlg.cs
Normal file
@ -0,0 +1,45 @@
|
||||
///
|
||||
/// Copyright (c) 2026 Sensus Slovensko a.s.
|
||||
///
|
||||
|
||||
using Results;
|
||||
using Results.Forms;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Windows.Forms;
|
||||
using TBF.Resources;
|
||||
|
||||
namespace TBF.Rig.Output.DB.ResultsWriter
|
||||
{
|
||||
public partial class ResultsWriterResultsDlg : Form
|
||||
{
|
||||
public IList<WMeterRsltItemSpec> SelectedItems
|
||||
{
|
||||
set { resultsConfigCtrl.SelectedItems = value; }
|
||||
get { return resultsConfigCtrl.SelectedItems; }
|
||||
}
|
||||
|
||||
public ResultsWriterResultsDlg()
|
||||
{
|
||||
InitializeComponent();
|
||||
|
||||
this.Icon = Properties.Resources.TBF_icon;
|
||||
resultsConfigCtrl.SupressTestIDColumn = true;
|
||||
}
|
||||
|
||||
private void ResultsWriterResultsDlg_Load(object sender, EventArgs e)
|
||||
{
|
||||
Text = "ResultsWriter configuration";
|
||||
okButton.Text = Strings.OkBtnText;
|
||||
cancelButton.Text = Strings.CancelBtnText;
|
||||
|
||||
resultsConfigCtrl.Unlocked = true;
|
||||
}
|
||||
|
||||
private void okButton_Click(object sender, EventArgs e)
|
||||
{
|
||||
DialogResult = DialogResult.OK;
|
||||
Close();
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -99,6 +99,7 @@ namespace TBF.Rig
|
||||
new Output.DataStorage.UniDataStorageWriter.Factory(),
|
||||
new Output.DB.DatabaseWriter.Factory(),
|
||||
new Output.DB.ProductionTracing.Factory(),
|
||||
new Output.DB.ResultsWriter.Factory(),
|
||||
new Output.DB.SaveDiverterCorrections.Factory(),
|
||||
new Output.DB.SaveFlowmeterCorrections.Factory(),
|
||||
new Output.DB.SensusOracle.Factory(),
|
||||
|
||||
@ -1236,6 +1236,22 @@
|
||||
</Compile>
|
||||
<Compile Include="Rig\Output\DB\ProductionTracing\Factory.cs" />
|
||||
<Compile Include="Rig\Output\DB\ProductionTracing\WMPart.cs" />
|
||||
<Compile Include="Rig\Output\DB\ResultsWriter\Factory.cs" />
|
||||
<Compile Include="Rig\Output\DB\ResultsWriter\ResultsWriter.cs" />
|
||||
<Compile Include="Rig\Output\DB\ResultsWriter\ResultsWriterCfg.cs" />
|
||||
<Compile Include="Rig\Output\DB\ResultsWriter\ResultsWriterCfgCtrl.cs">
|
||||
<SubType>UserControl</SubType>
|
||||
</Compile>
|
||||
<Compile Include="Rig\Output\DB\ResultsWriter\ResultsWriterCfgCtrl.Designer.cs">
|
||||
<DependentUpon>ResultsWriterCfgCtrl.cs</DependentUpon>
|
||||
</Compile>
|
||||
<Compile Include="Rig\Output\DB\ResultsWriter\ResultsWriterItemCfg.cs" />
|
||||
<Compile Include="Rig\Output\DB\ResultsWriter\ResultsWriterResultsDlg.cs">
|
||||
<SubType>Form</SubType>
|
||||
</Compile>
|
||||
<Compile Include="Rig\Output\DB\ResultsWriter\ResultsWriterResultsDlg.Designer.cs">
|
||||
<DependentUpon>ResultsWriterResultsDlg.cs</DependentUpon>
|
||||
</Compile>
|
||||
<Compile Include="Rig\Output\DB\SaveDiverterCorrections\Factory.cs" />
|
||||
<Compile Include="Rig\Output\DB\SaveDiverterCorrections\SaveDiverterCorr.cs" />
|
||||
<Compile Include="Rig\Output\DB\SaveDiverterCorrections\SaveDiverterCorrCfg.cs" />
|
||||
|
||||
Loading…
Reference in New Issue
Block a user