Files
Mapo-IOB-WIN/IOB-UT-NEXT/Config/IobConfTree.cs
T
2025-03-06 10:57:24 +01:00

756 lines
33 KiB
C#

using Newtonsoft.Json;
using YamlDotNet.Serialization.NamingConventions;
using YamlDotNet.Serialization;
using NLog;
using System.IO;
using System;
using static IOB_UT_NEXT.Config.EnumConf;
using System.Collections.Generic;
using System.Linq;
using IOB_UT_NEXT.Config;
using IOB_UT_NEXT.Config.Base;
using IOB_UT_NEXT.Config.Special;
using static System.Net.Mime.MediaTypeNames;
using System.Threading;
using System.Runtime.InteropServices;
// <Auto-Generated>
// This is here so CodeMaid doesn't reorganize this document
// </Auto-Generated>
namespace IOB_UT_NEXT.Config
{
/// <summary>
/// Albero configurazione globale IOB in formato serializable
/// </summary>
[Serializable]
public class IobConfTree
{
/// <summary>
/// Init classe configurazione
/// </summary>
public IobConfTree()
{
Log = LogManager.GetCurrentClassLogger();
}
/// <summary>
/// Init classe configurazione da file
/// </summary>
public IobConfTree(string confFilePath)
{
Log = LogManager.GetCurrentClassLogger();
if (File.Exists(confFilePath))
{
IobConfTree newConfObj = new IobConfTree();
// verifico TIPO file...
string fileExt = Path.GetExtension(confFilePath);
string fileName = Path.GetFileName(confFilePath);
string rawData = File.ReadAllText(confFilePath);
if (!string.IsNullOrEmpty(rawData))
{
// leggo in base al tipo...
switch (fileExt)
{
case "yaml":
case "yml":
var deserializer = new DeserializerBuilder()
.WithNamingConvention(CamelCaseNamingConvention.Instance)
.Build();
try
{
newConfObj = deserializer.Deserialize<IobConfTree>(rawData);
}
catch (Exception exc)
{
//lgError($"Eccezione in LoadFromYaml{Environment.NewLine}{exc}");
}
break;
default:
break;
}
if (newConfObj != null)
{
// ora copio in oggetto corrente...
General = newConfObj.General;
Device = newConfObj.Device;
SignalProc = newConfObj.SignalProc;
OptPar = newConfObj.OptPar;
MapoMes = newConfObj.MapoMes;
Special = newConfObj.Special;
TCDataConf = newConfObj.TCDataConf;
Actions = newConfObj.Actions;
// sovrascrivo filename
General.FileName = fileName;
}
}
}
}
/// <summary>
/// Restituisce un oggetto di conf leggendo INI ed effettuando conversione
/// </summary>
/// <param name="iniFilePath"></param>
/// <returns></returns>
public static IobConfTree LoadFromINI(string iniFilePath)
{
IobConfTree newConfObj = new IobConfTree();
try
{
// leggo file INI
IniFile fIni = new IniFile(iniFilePath);
string dirPath = Path.GetDirectoryName(iniFilePath);
string codIob = Path.GetFileNameWithoutExtension(iniFilePath);
// elenco valori OPT_Par già acquisiti da togliere dal dizionario generico in coda
List<string> exclOptPar = new List<string>();
// Dati generali (vendor, modello...)
newConfObj.General = new IobDto()
{
CodIOB = fIni.ReadString("IOB", "IOB_NAME", codIob),
FileName = Path.GetFileName(iniFilePath),
Customer = fIni.ReadString("TAGS", "Customer", "EgalWare"),
EnabRedisQue = bool.Parse(fIni.ReadString("IOB", "EnableRedisQueue", "true")),
MinDeltaSec = fIni.ReadInteger("IOB", "MinDeltaSec", 6),
RelVers = $"{System.Reflection.Assembly.GetExecutingAssembly().GetName().Version}",
WaitRecMsec = Convert.ToInt32(fIni.ReadString("OPTPAR", "WAIT_REC_MSEC", "90000")),
DisabWDST = bool.Parse(fIni.ReadString("OPTPAR", "DISABLE_SEND_WDST", "true"))
};
// da togliere da conf app...
int uiTimer = utils.CRI("timerIntMs");
string rawTimer = fIni.ReadString("OPTPAR", "timerIntMs", "");
if (!string.IsNullOrEmpty(rawTimer))
{
int.TryParse(rawTimer, out uiTimer);
}
// ultimo controllo: timer deve essere compreso tra 10 a 500 x evitare task troppo veloci o lenti...
uiTimer = uiTimer < 10 ? 10 : uiTimer;
uiTimer = uiTimer > 500 ? 500 : uiTimer;
// init struttura coi valori calcolati da conf...
newConfObj.General.Timers = new TimersDto()
{
MsUI = uiTimer,
MsVHF = uiTimer * 5 < 200 ? uiTimer * 5 : 200,
MsHF = uiTimer * utils.CRI("fastCount") < 1000 ? uiTimer * utils.CRI("fastCount") : 1000,
MsMF = uiTimer * utils.CRI("normCount") < 10000 ? uiTimer * utils.CRI("normCount") : 10000,
MsLF = uiTimer * utils.CRI("slowCount") < 6000 ? uiTimer * utils.CRI("slowCount") : 6000,
MsVLF = uiTimer * utils.CRI("verySlowCount") < 60000 ? uiTimer * utils.CRI("verySlowCount") : 60000,
MsSample = uiTimer * utils.CRI("sampleMemCount") < 300000 ? uiTimer * utils.CRI("sampleMemCount") : 300000,
};
exclOptPar.Add("WAIT_REC_MSEC");
exclOptPar.Add("DISABLE_SEND_WDST");
exclOptPar.Add("timerIntMs");
// tipo adapter// verifico tipo adapter
try
{
newConfObj.General.IobType = (tipoAdapter)Enum.Parse(typeof(tipoAdapter), fIni.ReadString("IOB", "CNCTYPE", "ND"));
}
catch (Exception exc)
{
newConfObj.General.IobType = tipoAdapter.ND;
string rawVal = fIni.ReadString("IOB", "CNCTYPE", "DEMO");
newConfObj.lgError($"Eccezione in conversione tipo adapter: richiesto {rawVal} | tipo non codificato...{Environment.NewLine}{exc}");
}
// Gestione conf ODL
newConfObj.Odl = new OdlDto()
{
AutoChangeOdl = bool.Parse(fIni.ReadString("OPTPAR", "AUTO_CHANGE_ODL", "false")),
ChangeOdlMode = fIni.ReadString("OPTPAR", "CHANGE_ODL_MODE", ""),
OdlDurationHours = fIni.ReadInteger("OPTPAR", "CHANGE_ODL_HOURS", 24),
IdleStateMin = fIni.ReadInteger("OPTPAR", "CHANGE_ODL_IDLE_MIN", 0),
// il change ODL al reset contapezzi può essere configurato in 2 modi: con chiave esplicita oppure con il CHANGE_ODL_MODE specifico...
ChangeOnResetCount = bool.Parse(fIni.ReadString("OPTPAR", "CHANGE_PZCOUNT_RESET", "false")) || (fIni.ReadString("OPTPAR", "CHANGE_ODL_MODE", "") == "PZCOUNT_RESET"),
// gestione precedente: bastava 1 solo pezzo pre...
ResetCountMinPre = fIni.ReadInteger("OPTPAR", "RESET_COUNT_PRE", 1),
// e reset a zero...
ResetCountMaxPost = fIni.ReadInteger("OPTPAR", "RESET_COUNT_POST", 0),
};
exclOptPar.Add("AUTO_CHANGE_ODL");
exclOptPar.Add("CHANGE_ODL_MODE");
exclOptPar.Add("CHANGE_ODL_HOURS");
exclOptPar.Add("CHANGE_ODL_IDLE_MIN");
exclOptPar.Add("CHANGE_PZCOUNT_RESET");
exclOptPar.Add("RESET_COUNT_PRE");
exclOptPar.Add("RESET_COUNT_POST");
newConfObj.Device = new DeviceDto()
{
DisabExeTask = bool.Parse(fIni.ReadString("IOB", "DIS_EXE_TASK", "false")),
DisabStateCh = bool.Parse(fIni.ReadString("IOB", "DIS_STATE_CH", "false")),
EnabPzCount = utils.CRB("enableContapezzi"),
PzCountDelay = utils.CRI("pzCountDelay"),
PzCountMode = fIni.ReadString("OPTPAR", "PZCOUNT_MODE", ""),
Vendor = fIni.ReadString("MACHINE", "VENDOR", "STEAMWARE"),
Model = fIni.ReadString("MACHINE", "MODEL", "ND"),
EnabProgName = bool.Parse(fIni.ReadString("CNC", "GETPRGNAME", "true")),
Connect = new ConnectionDto()
{
IpAddr = fIni.ReadString("CNC", "IP", "::1"),
PingIpAddr = fIni.ReadString("CNC", "PING_IP", fIni.ReadString("CNC", "IP", "::1")),
PingMsTimeout = fIni.ReadInteger("IOB", "PING_MS_TIMEOUT", 500),
Port = fIni.ReadString("CNC", "PORT", "0")
}
};
exclOptPar.Add("PZCOUNT_MODE");
// multi...
newConfObj.Device.IsMulti = Convert.ToBoolean(fIni.ReadString("OPTPAR", "IS_MULTI", "false")) || fIni.ReadString("OPTPAR", "IS_MULTI", "0") == "1";
exclOptPar.Add("IS_MULTI");
// BLINK
newConfObj.SignalProc.BlinkMaxCounter = Convert.ToInt32(fIni.ReadString("BLINK", "MAX_COUNTER_BLINK", "1"));
newConfObj.SignalProc.BlinkFilterMask = Convert.ToInt32(fIni.ReadString("BLINK", "BLINK_FILT", "0"));
newConfObj.TCDataConf.MaxDelayFactor = Convert.ToDouble(fIni.ReadString("OPTPAR", "TC_MAX_TC_FACTOR", "1.2").Replace(".", ","));
newConfObj.TCDataConf.Lambda = Convert.ToDouble(fIni.ReadString("OPTPAR", "TC_LAMBDA", "0.5").Replace(".", ","));
newConfObj.TCDataConf.MaxIncrPz = Convert.ToDouble(fIni.ReadString("OPTPAR", "TC_MAX_INCR", "5").Replace(".", ","));
exclOptPar.Add("TC_MAX_TC_FACTOR");
exclOptPar.Add("TC_LAMBDA");
exclOptPar.Add("TC_MAX_INCR");
// Server
string MpIp = fIni.ReadString("SERVER", "MPIP", "::1");
if (!string.IsNullOrEmpty(MpIp))
{
newConfObj.MapoMes.Transport = MpIp.StartsWith("https://") ? "https" : "http";
newConfObj.MapoMes.IpAddr = MpIp.Replace($"{newConfObj.MapoMes.Transport}://", ""); // tolgo http/https...
newConfObj.MapoMes.ClientInstall = "SteamWare";
}
string MpUrl = fIni.ReadString("SERVER", "MPURL", "");
if (!string.IsNullOrEmpty(MpUrl))
{
newConfObj.MapoMes.BaseAppUrl = $"{MpUrl}/".Replace("//", "/");
}
// Gestione contapezzi...
newConfObj.Counters.EnableSetPzCount = bool.Parse(fIni.ReadString("OPTPAR", "ENABLE_PZ_CNT", "false"));
newConfObj.Counters.EnableSetPzReq = bool.Parse(fIni.ReadString("OPTPAR", "ENABLE_PZ_REQ", "false"));
newConfObj.Counters.ResetOnStartSetup = bool.Parse(fIni.ReadString("OPTPAR", "ENABLE_PZ_RESET", "false"));
newConfObj.Counters.ResetOnStopSetup = bool.Parse(fIni.ReadString("OPTPAR", "ENABLE_PZ_RESET_stopSetup", "false"));
newConfObj.Counters.EnabSendPzcBlock = bool.Parse(fIni.ReadString("OPTPAR", "ENABLE_SEND_PZC_BLOCK", "false"));
newConfObj.Counters.SendPzcBlockMin = int.Parse(fIni.ReadString("OPTPAR", "MIN_SEND_PZC_BLOCK", "0"));
newConfObj.Counters.SendPzcBlockMax = int.Parse(fIni.ReadString("OPTPAR", "MAX_SEND_PZC_BLOCK", "100"));
exclOptPar.Add("ENABLE_PZ_CNT");
exclOptPar.Add("ENABLE_PZ_REQ");
exclOptPar.Add("ENABLE_PZ_RESET");
exclOptPar.Add("ENABLE_PZ_RESET_stopSetup");
exclOptPar.Add("ENABLE_SEND_PZC_BLOCK");
exclOptPar.Add("MIN_SEND_PZC_BLOCK");
exclOptPar.Add("MAX_SEND_PZC_BLOCK");
// gestione ODL
// Altro
newConfObj.IobMan.MinDeltaSec = fIni.ReadInteger("IOB", "MinDeltaSec", 6);
// OptPar
Dictionary<string, string> optParRead = new Dictionary<string, string>();
string[] optParRows = fIni.ReadSection("OPTPAR");
if (optParRows.Length > 0)
{
try
{
string[] kvp;
foreach (var item in optParRows)
{
kvp = item.Split('=');
// escludo valori già acquisiti...
if (!exclOptPar.Contains(kvp[0]))
{
optParRead.Add(kvp[0], kvp[1]);
}
}
newConfObj.lgDebug($"Caricati {optParRead.Count} parametri opzionali da OPTPAR");
}
catch (Exception exc)
{
newConfObj.lgError($"EXCEPTION in fase di lettura OPTPAR: {Environment.NewLine}{exc}");
}
}
// riordino alfabeticamente
optParRead = optParRead.OrderBy(x => x.Key).ToDictionary(x => x.Key, x => x.Value);
newConfObj.OptPar = optParRead;
newConfObj.Special = new SpecializedDto();
// verifico se ho conf json speciali: LUT decodifica PARAMETRI
if (optParRead.ContainsKey("PARAM_CONF"))
{
string jsonParams = optParRead["PARAM_CONF"];
if (!string.IsNullOrEmpty(jsonParams))
{
string jsonFileName = Path.Combine(dirPath, jsonParams);
if (File.Exists(jsonFileName))
{
newConfObj.lgInfo($"Apertura file {jsonFileName}");
using (StreamReader reader = new StreamReader(jsonFileName))
{
string jsonData = reader.ReadToEnd();
if (!string.IsNullOrEmpty(jsonData))
{
if (newConfObj.Memory == null)
{
newConfObj.Memory = new plcMemMapExt();
}
try
{
newConfObj.Memory = JsonConvert.DeserializeObject<plcMemMapExt>(jsonData);
}
catch (Exception exc)
{
newConfObj.lgError($"Eccezione in decodifica conf json{Environment.NewLine}{exc}");
}
}
else
{
newConfObj.lgError("Errore in loadMemConf: file json vuoto!");
}
}
}
}
else
{
newConfObj.lgInfo("loadMemConf: non trovata opzione PARAM_CONF in file INI");
}
}
// parametri opzionali Siemens
if (!string.IsNullOrEmpty(fIni.ReadString("CNC", "CPUTYPE", "")))
{
newConfObj.Special.SiemensConf = new SiemensDto();
// CPU Siemens
newConfObj.Special.SiemensConf.CpuType = fIni.ReadString("CNC", "CPUTYPE", "");
newConfObj.Special.SiemensConf.Rack = (short)fIni.ReadInteger("CNC", "RACK", 0);
newConfObj.Special.SiemensConf.Slot = (short)fIni.ReadInteger("CNC", "SLOT", 0);
// memoria Siemens!
newConfObj.Special.SiemensConf.MemAddrRead = fIni.ReadString("MEMORY", "ADDR_READ", "");
newConfObj.Special.SiemensConf.MemAddrWrite = fIni.ReadString("MEMORY", "ADDR_WRITE", "");
newConfObj.Special.SiemensConf.MemSizeRead = fIni.ReadInteger("MEMORY", "SIZE_READ", 0);
newConfObj.Special.SiemensConf.MemSizeWrite = fIni.ReadInteger("MEMORY", "SIZE_WRITE", 0);
}
// parametri opzionali BankConf
string[] memSection = fIni.ReadSection("MEMORY");
// in primis SE ho qualcosa...
if (memSection != null && memSection.Count() > 0)
{
// trasformo in array...
Dictionary<string, string> memDict = new Dictionary<string, string>();
foreach (var item in memSection)
{
// verifica preliminare NON sia commento (inizia per ";")
if (!item.StartsWith(";") && item.Contains("="))
{
var KVP = item.Split('=');
memDict.Add(KVP[0], KVP[1]);
}
}
// ora se ho qualcosa proseguo...
if (memDict.Count() > 0)
{
// cerco dati x popolare SigLUT
foreach (var item in memDict.Where(x => x.Key.StartsWith("BIT")))
{
if (newConfObj.Device.SigLUT.ContainsKey(item.Key))
{
newConfObj.Device.SigLUT[item.Key] = item.Value;
}
else
{
newConfObj.Device.SigLUT.Add(item.Key, item.Value);
}
}
// cerco dati specifici x popolare l'area Memoria (Fanuc/Mitsubischi/...)
if (memDict.Where(x => x.Key.StartsWith("AREA") || x.Key.StartsWith("PAR") || x.Key.StartsWith("SIGN")).Count() > 0)
{
// init info bank memoria...
if (newConfObj.Special.BankConf == null)
{
newConfObj.Special.BankConf = new MemBankDto();
}
// inizio setup prendendo quelli con valori addrSize
foreach (var item in memDict.Where(x => x.Key.EndsWith("SIZE")))
{
int addrSize = 0;
int.TryParse(item.Value, out addrSize);
// salvo solo quelli con valori addrSize > 0
if (addrSize > 0)
{
string mId = item.Key.Replace("_SIZE", "");
// cerco record inizio
var valStart = memDict.Where(x => x.Key == item.Key.Replace("_SIZE", "_START")).Select(x => x.Value).FirstOrDefault();
if (!string.IsNullOrEmpty(valStart))
{
int addrStart = 0;
int.TryParse(valStart, out addrStart);
var memArea = new Mem.MemAreaDto()
{
Start = addrStart,
Size = addrSize
};
if (newConfObj.Special.BankConf.AreaConf.ContainsKey(mId))
{
newConfObj.Special.BankConf.AreaConf[mId] = memArea;
}
else
{
newConfObj.Special.BankConf.AreaConf.Add(mId, memArea);
}
}
}
}
}
}
}
// salvo eventuale memTrace...
if (!string.IsNullOrEmpty(fIni.ReadString("OPTPAR", "MEM_2_TRACE", "")))
{
if (newConfObj.Special.BankConf == null)
{
newConfObj.Special.BankConf = new MemBankDto();
}
newConfObj.Special.BankConf.Mem2Trace = fIni.ReadString("OPTPAR", "MEM_2_TRACE", "");
exclOptPar.Add("MEM_2_TRACE");
}
// gestione speciale x type MBus
if ($"{newConfObj.General.IobType}".StartsWith("MODBUS_TCP"))
{
ModBusTcpParamConf newMBusPar = new ModBusTcpParamConf()
{
memAddrRead = fIni.ReadString("MEMORY", "ADDR_READ", ""),
memAddrWrite = fIni.ReadString("MEMORY", "ADDR_WRITE", ""),
memSizeRead = fIni.ReadInteger("MEMORY", "SIZE_READ", 0),
memSizeWrite = fIni.ReadInteger("MEMORY", "SIZE_WRITE", 0),
holdRegBaseAddr = fIni.ReadInteger("MEMORY", "HR_BASE_ADDR", 40001),
useCalcBaseAddr = fIni.ReadBoolean("MEMORY", "CALC_BASE_ADDR", true),
// valore delta base e shift
deltaBase = fIni.ReadInteger("MEMORY", "DELTA_BASE", 0),
indexLutCorr = fIni.ReadInteger("MEMORY", "INDEX_LUT_CORR", 0),
// verifico eventuale parametro memoria estesa (non 0...10'000 ma 0...xFFFF=65536)
modbusExtReg = fIni.ReadBoolean("MEMORY", "MODBUS_EXT_REG")
};
newConfObj.Special.ModbusConf = newMBusPar;
}
// alla fine verifico eventuali eccezioni alla gestione pzCount con abilitazione esplicita
if (!string.IsNullOrEmpty(newConfObj.OptParGet("ENABLE_PZCOUNT")))
{
newConfObj.Device.EnabPzCount = newConfObj.OptParGet("ENABLE_PZCOUNT") == "TRUE";
exclOptPar.Add("ENABLE_PZCOUNT");
}
// o al contrario con disabilitazione esplicita
if (!string.IsNullOrEmpty(newConfObj.OptParGet("DISABLE_PZCOUNT")))
{
newConfObj.Device.EnabPzCount = !(newConfObj.OptParGet("DISABLE_PZCOUNT") == "TRUE");
exclOptPar.Add("DISABLE_PZCOUNT");
}
// gestione override idx articoli...
if (!string.IsNullOrEmpty(newConfObj.OptParGet("NUM_ART_CHR_TRIM")))
{
string NUM_ART_CHR_TRIM = newConfObj.OptParGet("NUM_ART_CHR_TRIM");
bool.TryParse(NUM_ART_CHR_TRIM, out var numArtCharTrim);
newConfObj.Device.NumArtCharTrim = numArtCharTrim;
exclOptPar.Add("NUM_ART_CHR_TRIM");
}
}
catch (Exception exc)
{
newConfObj.lgError($"EXCEPTION in decodifica IobConfTree: {Environment.NewLine}{exc}");
}
return newConfObj;
}
/// <summary>
/// Calcola la scadenza in ms del timer richiesto
/// </summary>
/// <param name="ciclo">Tipo di ciclo richiesto x estrarre da obj conf</param>
/// <param name="percFact">Fattore di perturbazione random come valore +/- da aggiungere in %
/// default 0 = deterministico
/// Range ammesso: 0..0.5</param>
/// <returns></returns>
public int TimerMs(gatherCycle ciclo, double percFact = 0)
{
// default a 1sec...
int answ = 1000;
// verifica quale valore recuperare
switch (ciclo)
{
case gatherCycle.VHF:
answ = General.Timers.MsVHF;
break;
case gatherCycle.HF:
answ = General.Timers.MsHF;
break;
case gatherCycle.MF:
answ = General.Timers.MsMF;
break;
case gatherCycle.LF:
answ = General.Timers.MsLF;
break;
case gatherCycle.VLF:
answ = General.Timers.MsVLF;
break;
default:
break;
}
// se richeisto perturbo...
if (percFact != 0)
{
// prendo valore in modulo
percFact = Math.Abs(percFact);
// verifico sia < 50%...
percFact = percFact > 0.5 ? 0.5 : percFact;
// mi baso su un fattore 1'000 da perturbare
int mult = 1000;
answ = (answ * rand.Next((int)(mult * (1 - percFact)), (int)(mult * (1 + percFact))) / mult);
}
return answ;
}
/// <summary>
/// Info generali delative all'IOB impiegato
/// </summary>
public IobDto General { get; set; } = new IobDto();
/// <summary>
/// Parametri server Mapo MES
/// </summary>
public ServerMapoDto MapoMes { get; set; } = new ServerMapoDto();
/// <summary>
/// Setup info verso IOB-MAN
/// </summary>
public IobManDto IobMan { get; set; } = new IobManDto();
/// <summary>
/// Gestione specifica azioni sul contapezzi
/// </summary>
public CounterDto Counters { get; set; } = new CounterDto();
/// <summary>
/// Gestione configurazione parametri relativi ai FluxLog
/// </summary>
public FluxLogDto FluxLog { get; set; } = new FluxLogDto();
/// <summary>
/// Configurazione specifica gestione ODL
/// </summary>
public OdlDto Odl { get; set; } = new OdlDto();
/// <summary>
/// Info relative al device interconnesso
/// </summary>
public DeviceDto Device { get; set; } = new DeviceDto();
/// <summary>
/// Struttura memoria PLC x lettura/scrittura
/// </summary>
public plcMemMapExt Memory { get; set; }
/// <summary>
/// Setup processing dati in ingresso (es: blink segnali)
/// </summary>
public InputSignalDto SignalProc { get; set; } = new InputSignalDto();
/// <summary>
/// Dati relativi ai parametri gestione tempo ciclo
/// </summary>
public TCDataDto TCDataConf { get; set; } = new TCDataDto();
/// <summary>
/// Configurazione Allarmi
/// </summary>
public AlarmDto Alarms { get; set; }
/// <summary>
/// Configurazione speciale comportamenti IOB (es setup)
/// </summary>
public ActionDto Actions { get; set; }
/// <summary>
/// Dizionario delle traduzioni termini chiave/valore
/// </summary>
public Dictionary<string, string> ItemTranslation { get; set; } = new Dictionary<string, string>();
/// <summary>
/// Recupera traduzoine item richiesta
/// </summary>
/// <param name="key"></param>
/// <returns></returns>
public string ItemTranslationGet(string key)
{
string answ = "";
if (ItemTranslation != null && ItemTranslation.ContainsKey(key))
{
answ = ItemTranslation[key];
}
return answ;
}
/// <summary>
/// Dizionario dei parametri opzionali
/// </summary>
public Dictionary<string, string> OptPar { get; set; } = new Dictionary<string, string>();
/// <summary>
/// Recupera valore della chiave specifica richiesta
/// </summary>
/// <param name="key"></param>
/// <returns></returns>
public string OptParGet(string key)
{
string answ = "";
if (OptPar != null && OptPar.Count > 0 && OptPar.ContainsKey(key))
{
answ = OptPar[key];
}
return answ;
}
/// <summary>
/// Configurazione speciale/opzionale per tipo IOB
/// </summary>
public SpecializedDto Special { get; set; }
#region Metodi Serializzazione
/// <summary>
/// Restituisce conf serializzata in formato JSON
/// </summary>
/// <param name="filePath"></param>
/// <returns></returns>
public string GetJson()
{
string rawdata = JsonConvert.SerializeObject(this, Formatting.Indented);
return rawdata;
}
/// <summary>
/// Restituisce conf serializzata in formato YAML
/// </summary>
/// <param name="filePath"></param>
/// <returns></returns>
public string GetYaml()
{
// opzioni alternative: PascalCaseNamingConvention (iniziale masiucola) o lowerCaseNamingConvention
var serializer = new SerializerBuilder()
.WithNamingConvention(CamelCaseNamingConvention.Instance)
.Build();
var rawdata = serializer.Serialize(this);
return rawdata;
}
#endregion
#region Metodi Load/Save
/// <summary>
/// Scrive conf serializzata in formato JSON
/// </summary>
/// <param name="filePath"></param>
/// <returns></returns>
public bool SaveJson(string filePath)
{
bool answ = false;
try
{
string rawdata = GetJson();
File.WriteAllText(filePath, rawdata);
answ = true;
}
catch
{ }
return answ;
}
/// <summary>
/// Scrive conf serializzata in formato YAML
/// </summary>
/// <param name="filePath"></param>
/// <returns></returns>
public bool SaveYaml(string filePath)
{
bool answ = false;
try
{
var rawdata = GetYaml();
File.WriteAllText(filePath, rawdata);
answ = true;
}
catch
{ }
return answ;
}
#endregion
#region Logging
/// <summary>
/// oggetto logging
/// </summary>
protected Logger Log;// = LogManager.GetCurrentClassLogger();
/// <summary>
/// Effettua logging DEBUG corretto impostanto anche la variabile IOB prima di scrivere...
/// </summary>
/// <param name="txt2log"></param>
protected void lgDebug(string txt2log)
{
Log.Factory.Configuration.Variables["codIOB"] = General.CodIOB;
Log.Debug(txt2log);
}
/// <summary>
/// Effettua logging ERROR corretto impostanto anche la variabile IOB prima di scrivere...
/// </summary>
/// <param name="txt2log"></param>
protected void lgError(string txt2log)
{
if (!string.IsNullOrEmpty(txt2log))
{
Log.Factory.Configuration.Variables["codIOB"] = General.CodIOB;
Log.Error(txt2log);
}
}
/// <summary>
/// Effettua logging INFO corretto impostanto anche la variabile IOB prima di scrivere...
/// </summary>
/// <param name="txt2log"></param>
protected void lgInfo(string txt2log)
{
Log.Factory.Configuration.Variables["codIOB"] = General.CodIOB;
Log.Info(txt2log);
}
/// <summary>
/// Effettua logging TRACE corretto impostanto anche la variabile IOB prima di scrivere...
/// </summary>
/// <param name="txt2log"></param>
protected void lgTrace(string txt2log)
{
Log.Factory.Configuration.Variables["codIOB"] = General.CodIOB;
Log.Trace(txt2log);
}
#endregion
#region Area Private
/// <summary>
/// Generatore random x gestione non deterministica
/// </summary>
private Random rand = new Random();
#endregion Area Private
}
}