antes de eliminar las estructuras de Begin block de los json

This commit is contained in:
Miguel 2025-05-18 01:04:24 +02:00
parent 00f3b6d2ec
commit e85c0c169d
4 changed files with 986 additions and 423 deletions

View File

@ -1,9 +1,9 @@
--- Log de Ejecución: x4.py ---
Grupo: S7_DB_Utils
Directorio de Trabajo: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001
Inicio: 2025-05-17 21:37:42
Fin: 2025-05-17 21:37:42
Duración: 0:00:00.131741
Inicio: 2025-05-18 00:51:35
Fin: 2025-05-18 00:51:35
Duración: 0:00:00.110751
Estado: SUCCESS (Código de Salida: 0)
--- SALIDA ESTÁNDAR (STDOUT) ---
@ -23,11 +23,11 @@ INFO: Usando '_begin_block_assignments_ordered' para generar bloque BEGIN de DB
Archivo S7 reconstruido generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_format.txt
Archivo Markdown de documentación generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_format.md
--- Procesando archivo JSON: db1001_format_updated.json ---
Archivo JSON 'db1001_format_updated.json' cargado correctamente.
--- Procesando archivo JSON: db1001_updated.json ---
Archivo JSON 'db1001_updated.json' cargado correctamente.
INFO: Usando '_begin_block_assignments_ordered' para generar bloque BEGIN de DB 'HMI_Blender_Parameters'.
Archivo S7 reconstruido generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_format_updated.txt
Archivo Markdown de documentación generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_format_updated.md
Archivo S7 reconstruido generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_updated.txt
Archivo Markdown de documentación generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_updated.md
--- Proceso de generación de documentación completado ---

View File

@ -1,28 +1,309 @@
--- Log de Ejecución: x7_value_updater.py ---
Grupo: S7_DB_Utils
Directorio de Trabajo: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001
Inicio: 2025-05-17 23:48:43
Fin: 2025-05-17 23:48:43
Duración: 0:00:00.106052
Inicio: 2025-05-18 00:51:17
Fin: 2025-05-18 00:51:18
Duración: 0:00:00.223903
Estado: SUCCESS (Código de Salida: 0)
--- SALIDA ESTÁNDAR (STDOUT) ---
Using working directory: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001
Found _data file: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\db1001_data.db
Found _format file: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\db1001_format.db
Parsing S7 file: db1001_data.db...
Serializing to JSON: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json\db1001_data_data.json
JSON saved: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json\db1001_data_data.json
Parsing S7 file: db1001_format.db...
Serializing to JSON: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json\db1001_format_format.json
JSON saved: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json\db1001_format_format.json
Comparing structure of DB: HMI_Blender_Parameters
La estructura del DB 'HMI_Blender_Parameters' es compatible.
Los archivos JSON se guardarán en: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json
Se encontraron 1 pares de archivos para procesar.
All DB structures are compatible. Proceeding to generate _updated file.
INFO: Usando '_begin_block_assignments_ordered' para generar bloque BEGIN de DB 'HMI_Blender_Parameters'.
--- Procesando par de archivos ---
Data file: db1001_data.db
Format file: db1001_format.db
Parseando archivo data: db1001_data.db
Parseando archivo format: db1001_format.db
Archivos JSON generados: db1001_data.json y db1001_format.json
Aplanando variables por offset...
Comparando estructuras: 251 variables en _data, 251 variables en _format
Successfully generated _updated S7 file: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\db1001_updated.db
Los archivos son compatibles. Creando el archivo _updated...
Mapeando STAT0.STAT1.STAT2 -> Processor_Options.Blender_OPT._ModelNum (offset 0.0)
Mapeando STAT0.STAT1.STAT3 -> Processor_Options.Blender_OPT._CO2_Offset (offset 2.0)
Mapeando STAT0.STAT1.STAT4 -> Processor_Options.Blender_OPT._MaxSyrDeltaBrix (offset 6.0)
Mapeando STAT0.STAT1.STAT5 -> Processor_Options.Blender_OPT._BrixMeter (offset 10.0)
Mapeando STAT0.STAT1.STAT6 -> Processor_Options.Blender_OPT.Spare101 (offset 10.1)
Mapeando STAT0.STAT1.STAT7 -> Processor_Options.Blender_OPT._TrackH2OEnable (offset 10.2)
Mapeando STAT0.STAT1.STAT8 -> Processor_Options.Blender_OPT._PAmPDSType (offset 10.3)
Mapeando STAT0.STAT1.STAT9 -> Processor_Options.Blender_OPT._HistoricalTrends (offset 10.4)
Mapeando STAT0.STAT1.STAT10 -> Processor_Options.Blender_OPT._PowerMeter (offset 10.5)
Mapeando STAT0.STAT1.STAT11 -> Processor_Options.Blender_OPT._Report (offset 10.6)
Mapeando STAT0.STAT1.STAT12 -> Processor_Options.Blender_OPT._Balaiage (offset 10.7)
Mapeando STAT0.STAT1.STAT13 -> Processor_Options.Blender_OPT._Valves_FullFeedback (offset 11.0)
Mapeando STAT0.STAT1.STAT14 -> Processor_Options.Blender_OPT._Valves_SingleFeedback (offset 11.1)
Mapeando STAT0.STAT1.STAT15 -> Processor_Options.Blender_OPT._PumpsSafetySwitches (offset 11.2)
Mapeando STAT0.STAT1.STAT16 -> Processor_Options.Blender_OPT._SurgeProtectionAct (offset 11.3)
Mapeando STAT0.STAT1.STAT17 -> Processor_Options.Blender_OPT._DBC_Type (offset 11.4)
Mapeando STAT0.STAT1.STAT18 -> Processor_Options.Blender_OPT._CO2InletMeter (offset 11.5)
Mapeando STAT0.STAT1.STAT19 -> Processor_Options.Blender_OPT._ProductO2Meter (offset 11.6)
Mapeando STAT0.STAT1.STAT20 -> Processor_Options.Blender_OPT._CopressedAirInletMeter (offset 11.7)
Mapeando STAT0.STAT1.STAT21 -> Processor_Options.Blender_OPT._MeterType (offset 12.0)
Mapeando STAT0.STAT1.STAT22 -> Processor_Options.Blender_OPT._MeterReceiveOnly (offset 14.0)
Mapeando STAT0.STAT1.STAT23 -> Processor_Options.Blender_OPT._SyrBrixMeter (offset 14.1)
Mapeando STAT0.STAT1.STAT24 -> Processor_Options.Blender_OPT._Flooding_Start_Up (offset 14.2)
Mapeando STAT0.STAT1.STAT25 -> Processor_Options.Blender_OPT._FastChangeOverEnabled (offset 14.3)
Mapeando STAT0.STAT1.STAT26 -> Processor_Options.Blender_OPT._WaterInletMeter (offset 14.4)
Mapeando STAT0.STAT1.STAT27 -> Processor_Options.Blender_OPT._BlendFillSystem (offset 14.5)
Mapeando STAT0.STAT1.STAT28 -> Processor_Options.Blender_OPT._TrackFillerSpeed (offset 14.6)
Mapeando STAT0.STAT1.STAT29 -> Processor_Options.Blender_OPT._SignalExchange (offset 16.0)
Mapeando STAT0.STAT1.STAT30 -> Processor_Options.Blender_OPT._CoolerPresent (offset 18.0)
Mapeando STAT0.STAT1.STAT31 -> Processor_Options.Blender_OPT._CoolerControl (offset 20.0)
Mapeando STAT0.STAT1.STAT32 -> Processor_Options.Blender_OPT._CoolerType (offset 22.0)
Mapeando STAT0.STAT1.STAT33 -> Processor_Options.Blender_OPT._LocalCIP (offset 24.0)
Mapeando STAT0.STAT1.STAT34 -> Processor_Options.Blender_OPT._ICS_CustomerHotWater (offset 24.1)
Mapeando STAT0.STAT1.STAT35 -> Processor_Options.Blender_OPT._ICS_CustomerChemRecov (offset 24.2)
Mapeando STAT0.STAT1.STAT36 -> Processor_Options.Blender_OPT._CIPSignalExchange (offset 24.3)
Mapeando STAT0.STAT1.STAT37 -> Processor_Options.Blender_OPT._ICS_CustomerChemicals (offset 24.4)
Mapeando STAT0.STAT1.STAT38 -> Processor_Options.Blender_OPT._CarboPresent (offset 24.5)
Mapeando STAT0.STAT1.STAT39 -> Processor_Options.Blender_OPT._InverterSyrupPumpPPP302 (offset 24.6)
Mapeando STAT0.STAT1.STAT40 -> Processor_Options.Blender_OPT._InverterWaterPumpPPN301 (offset 24.7)
Mapeando STAT0.STAT1.STAT41 -> Processor_Options.Blender_OPT._DoubleDeair (offset 25.0)
Mapeando STAT0.STAT1.STAT42 -> Processor_Options.Blender_OPT._DeairPreMixed (offset 25.1)
Mapeando STAT0.STAT1.STAT43 -> Processor_Options.Blender_OPT._Deaireation (offset 25.2)
Mapeando STAT0.STAT1.STAT44 -> Processor_Options.Blender_OPT._StillWaterByPass (offset 25.3)
Mapeando STAT0.STAT1.STAT45 -> Processor_Options.Blender_OPT._ManifoldSetting (offset 25.4)
Mapeando STAT0.STAT1.STAT46 -> Processor_Options.Blender_OPT._InverterProdPumpPPM303 (offset 25.5)
Mapeando STAT0.STAT1.STAT47 -> Processor_Options.Blender_OPT._SidelCip (offset 25.6)
Mapeando STAT0.STAT1.STAT48 -> Processor_Options.Blender_OPT._EthernetCom_CpuPN_CP (offset 25.7)
Mapeando STAT0.STAT1.STAT49 -> Processor_Options.Blender_OPT._2ndOutlet (offset 26.0)
Mapeando STAT0.STAT1.STAT50 -> Processor_Options.Blender_OPT._Promass (offset 28.0)
Mapeando STAT0.STAT1.STAT51 -> Processor_Options.Blender_OPT._WaterPromass (offset 30.0)
Mapeando STAT0.STAT1.STAT52 -> Processor_Options.Blender_OPT._ProductConductimeter (offset 30.1)
Mapeando STAT0.STAT1.STAT53 -> Processor_Options.Blender_OPT._ICS_CustomerH2ORecov (offset 30.2)
Mapeando STAT0.STAT1.STAT54 -> Processor_Options.Blender_OPT.Spare303 (offset 30.3)
Mapeando STAT0.STAT1.STAT55 -> Processor_Options.Blender_OPT._CO2_GAS2_Injection (offset 30.4)
Mapeando STAT0.STAT1.STAT56 -> Processor_Options.Blender_OPT._InverterVacuuPumpPPN304 (offset 30.5)
Mapeando STAT0.STAT1.STAT57 -> Processor_Options.Blender_OPT._InverterBoostPumpPPM307 (offset 30.6)
Mapeando STAT0.STAT1.STAT58 -> Processor_Options.Blender_OPT._RunOut_Water (offset 30.7)
Mapeando STAT0.STAT1.STAT59 -> Processor_Options.Blender_OPT._FlowMeterType (offset 31.0)
Mapeando STAT0.STAT1.STAT60 -> Processor_Options.Blender_OPT._SidelFiller (offset 31.1)
Mapeando STAT0.STAT1.STAT61 -> Processor_Options.Blender_OPT._Simulation (offset 31.2)
Mapeando STAT0.STAT1.STAT62 -> Processor_Options.Blender_OPT._ProductCoolingCTRL (offset 31.3)
Mapeando STAT0.STAT1.STAT63 -> Processor_Options.Blender_OPT._ChillerCTRL (offset 31.4)
Mapeando STAT0.STAT1.STAT64 -> Processor_Options.Blender_OPT._CO2_SterileFilter (offset 31.5)
Mapeando STAT0.STAT1.STAT65 -> Processor_Options.Blender_OPT._InverterRecirPumpPPM306 (offset 31.6)
Mapeando STAT0.STAT1.STAT66 -> Processor_Options.Blender_OPT._ProdPressReleaseRVM304 (offset 31.7)
Mapeando STAT0.STAT1.STAT67 -> Processor_Options.Blender_OPT._VacuumPump (offset 32.0)
Mapeando STAT0.STAT1.STAT68 -> Processor_Options.Blender_OPT._GAS2InjectionType (offset 34.0)
Mapeando STAT0.STAT1.STAT69 -> Processor_Options.Blender_OPT._InjectionPress_Ctrl (offset 36.0)
Mapeando STAT0.STAT1.STAT70 -> Processor_Options.Blender_OPT._ProdPressureType (offset 38.0)
Mapeando STAT0.STAT1.STAT71 -> Processor_Options.Blender_OPT._CIPHeatType (offset 40.0)
Mapeando STAT0.STAT1.STAT72 -> Processor_Options.Blender_OPT._EHS_NrRes (offset 42.0)
Mapeando STAT73[1] -> Spare1 (offset 44.0)
Mapeando STAT73[2] -> Spare1 (offset 44.0)
Mapeando STAT73[3] -> Spare1 (offset 44.0)
Mapeando STAT73[4] -> Spare1 (offset 44.0)
Mapeando STAT73[5] -> Spare1 (offset 44.0)
Mapeando STAT73[6] -> Spare1 (offset 44.0)
Mapeando STAT73[7] -> Spare1 (offset 44.0)
Mapeando STAT73[8] -> Spare1 (offset 44.0)
Mapeando STAT73[9] -> Spare1 (offset 44.0)
Mapeando STAT74 -> _RVM301_DeadBand (offset 62.0)
Mapeando STAT75 -> _RVM301_Kp (offset 66.0)
Mapeando STAT76.STAT77 -> Actual_Recipe_Parameters._Name (offset 70.0)
Mapeando STAT76.STAT78 -> Actual_Recipe_Parameters._EnProdTemp (offset 104.0)
Mapeando STAT76.STAT79 -> Actual_Recipe_Parameters._SyrFlushing (offset 104.1)
Mapeando STAT76.STAT80 -> Actual_Recipe_Parameters._GAS2_Injection (offset 104.2)
Mapeando STAT76.STAT81 -> Actual_Recipe_Parameters._Eq_Pression_Selected (offset 104.3)
Mapeando STAT76.STAT82 -> Actual_Recipe_Parameters._DeoxStripEn (offset 104.4)
Mapeando STAT76.STAT83 -> Actual_Recipe_Parameters._DeoxVacuumEn (offset 104.5)
Mapeando STAT76.STAT84 -> Actual_Recipe_Parameters._DeoxPreMixed (offset 104.6)
Mapeando STAT76.STAT85 -> Actual_Recipe_Parameters._EnBlowOffProdPipeCO2Fil (offset 104.7)
Mapeando STAT76.STAT86 -> Actual_Recipe_Parameters._WaterSelection (offset 105.0)
Mapeando STAT76.STAT87 -> Actual_Recipe_Parameters._FillerNextRecipeNum (offset 106.0)
Mapeando STAT76.STAT88 -> Actual_Recipe_Parameters._BottleShape (offset 107.0)
Mapeando STAT76.STAT89 -> Actual_Recipe_Parameters._Type (offset 108.0)
Mapeando STAT76.STAT90 -> Actual_Recipe_Parameters._ProdMeterRecipeNum (offset 110.0)
Mapeando STAT76.STAT91 -> Actual_Recipe_Parameters._SyrupBrix (offset 112.0)
Mapeando STAT76.STAT92 -> Actual_Recipe_Parameters._SyrupDensity (offset 116.0)
Mapeando STAT76.STAT93 -> Actual_Recipe_Parameters._SyrupFactor (offset 120.0)
Mapeando STAT76.STAT94 -> Actual_Recipe_Parameters._ProductBrix (offset 124.0)
Mapeando STAT76.STAT95 -> Actual_Recipe_Parameters._ProductionRate (offset 128.0)
Mapeando STAT76.STAT96 -> Actual_Recipe_Parameters._Ratio (offset 132.0)
Mapeando STAT76.STAT97 -> Actual_Recipe_Parameters._ProdBrixOffset (offset 136.0)
Mapeando STAT76.STAT98 -> Actual_Recipe_Parameters._CO2Vols (offset 140.0)
Mapeando STAT76.STAT99 -> Actual_Recipe_Parameters._CO2Fact (offset 144.0)
Mapeando STAT76.STAT100 -> Actual_Recipe_Parameters._ProdTankPress (offset 148.0)
Mapeando STAT76.STAT101 -> Actual_Recipe_Parameters._SP_ProdTemp (offset 152.0)
Mapeando STAT76.STAT102 -> Actual_Recipe_Parameters._PrdTankMinLevel (offset 156.0)
Mapeando STAT76.STAT103 -> Actual_Recipe_Parameters._WaterValveSave (offset 160.0)
Mapeando STAT76.STAT104 -> Actual_Recipe_Parameters._SyrupValveSave (offset 164.0)
Mapeando STAT76.STAT105 -> Actual_Recipe_Parameters._CarboCO2ValveSave (offset 168.0)
Mapeando STAT76.STAT106 -> Actual_Recipe_Parameters._ProdMeterHighBrix (offset 172.0)
Mapeando STAT76.STAT107 -> Actual_Recipe_Parameters._ProdMeterLowBrix (offset 176.0)
Mapeando STAT76.STAT108 -> Actual_Recipe_Parameters._ProdMeterHighCO2 (offset 180.0)
Mapeando STAT76.STAT109 -> Actual_Recipe_Parameters._ProdMeterLowCO2 (offset 184.0)
Mapeando STAT76.STAT110 -> Actual_Recipe_Parameters._ProdMeter_ZeroCO2 (offset 188.0)
Mapeando STAT76.STAT111 -> Actual_Recipe_Parameters._ProdMeter_ZeroBrix (offset 192.0)
Mapeando STAT76.STAT112 -> Actual_Recipe_Parameters._ProdHighCond (offset 196.0)
Mapeando STAT76.STAT113 -> Actual_Recipe_Parameters._ProdLowCond (offset 200.0)
Mapeando STAT76.STAT114 -> Actual_Recipe_Parameters._BottleSize (offset 204.0)
Mapeando STAT76.STAT115 -> Actual_Recipe_Parameters._FillingValveHead_SP (offset 208.0)
Mapeando STAT76.STAT116 -> Actual_Recipe_Parameters._SyrMeter_ZeroBrix (offset 212.0)
Mapeando STAT76.STAT117 -> Actual_Recipe_Parameters._FirstProdExtraCO2Fact (offset 216.0)
Mapeando STAT76.STAT118 -> Actual_Recipe_Parameters._Gas2Vols (offset 220.0)
Mapeando STAT76.STAT119 -> Actual_Recipe_Parameters._Gas2Fact (offset 224.0)
Mapeando STAT76.STAT120 -> Actual_Recipe_Parameters._SyrupPumpPressure (offset 228.0)
Mapeando STAT76.STAT121 -> Actual_Recipe_Parameters._WaterPumpPressure (offset 232.0)
Mapeando STAT76.STAT122 -> Actual_Recipe_Parameters._CO2_Air_N2_PressSelect (offset 236.0)
Mapeando STAT76.STAT123 -> Actual_Recipe_Parameters._KFactRVM304BlowOff (offset 238.0)
Mapeando STAT76.STAT124 -> Actual_Recipe_Parameters._ProdRecircPumpFreq (offset 242.0)
Mapeando STAT76.STAT125 -> Actual_Recipe_Parameters._ProdBoosterPumpPress (offset 246.0)
Mapeando STAT76.STAT126 -> Actual_Recipe_Parameters._ProdSendPumpFreq (offset 250.0)
Mapeando STAT127[1] -> Spare2 (offset 254.0)
Mapeando STAT127[2] -> Spare2 (offset 254.0)
Mapeando STAT127[3] -> Spare2 (offset 254.0)
Mapeando STAT127[4] -> Spare2 (offset 254.0)
Mapeando STAT127[5] -> Spare2 (offset 254.0)
Mapeando STAT128 -> Next_Recipe_Name (offset 264.0)
Mapeando STAT129 -> Next_Recipe_Number (offset 298.0)
Mapeando STAT130[1] -> Spare3 (offset 300.0)
Mapeando STAT130[2] -> Spare3 (offset 300.0)
Mapeando STAT130[3] -> Spare3 (offset 300.0)
Mapeando STAT130[4] -> Spare3 (offset 300.0)
Mapeando STAT130[5] -> Spare3 (offset 300.0)
Mapeando STAT130[6] -> Spare3 (offset 300.0)
Mapeando STAT130[7] -> Spare3 (offset 300.0)
Mapeando STAT130[8] -> Spare3 (offset 300.0)
Mapeando STAT130[9] -> Spare3 (offset 300.0)
Mapeando STAT130[10] -> Spare3 (offset 300.0)
Mapeando STAT130[11] -> Spare3 (offset 300.0)
Mapeando STAT130[12] -> Spare3 (offset 300.0)
Mapeando STAT130[13] -> Spare3 (offset 300.0)
Mapeando STAT130[14] -> Spare3 (offset 300.0)
Mapeando STAT130[15] -> Spare3 (offset 300.0)
Mapeando STAT130[16] -> Spare3 (offset 300.0)
Mapeando STAT130[17] -> Spare3 (offset 300.0)
Mapeando STAT130[18] -> Spare3 (offset 300.0)
Mapeando STAT131.STAT132 -> ProcessSetup.Spare000 (offset 336.0)
Mapeando STAT131.STAT133 -> ProcessSetup.Spare040 (offset 340.0)
Mapeando STAT131.STAT134 -> ProcessSetup._KWaterLoss (offset 344.0)
Mapeando STAT131.STAT135 -> ProcessSetup._KSyrupLoss (offset 348.0)
Mapeando STAT131.STAT136 -> ProcessSetup._KProdLoss (offset 352.0)
Mapeando STAT131.STAT137 -> ProcessSetup._KPPM303 (offset 356.0)
Mapeando STAT131.STAT138 -> ProcessSetup._BaialageRVM301OVMin (offset 360.0)
Mapeando STAT131.STAT139 -> ProcessSetup._SyrupLinePressure (offset 364.0)
Mapeando STAT131.STAT140 -> ProcessSetup._CIPRMM301OV (offset 368.0)
Mapeando STAT131.STAT141 -> ProcessSetup._CIPRMP302OV (offset 372.0)
Mapeando STAT131.STAT142 -> ProcessSetup._CIPTM301MinLevel (offset 376.0)
Mapeando STAT131.STAT143 -> ProcessSetup._CIPTM301MaxLevel (offset 380.0)
Mapeando STAT131.STAT144 -> ProcessSetup._CIPPPM303Freq (offset 384.0)
Mapeando STAT131.STAT145 -> ProcessSetup._CIPTP301MinLevel (offset 388.0)
Mapeando STAT131.STAT146 -> ProcessSetup._CIPTP301MaxLevel (offset 392.0)
Mapeando STAT131.STAT147 -> ProcessSetup._RinseRMM301OV (offset 396.0)
Mapeando STAT131.STAT148 -> ProcessSetup._RinseRMP302OV (offset 400.0)
Mapeando STAT131.STAT149 -> ProcessSetup._RinseTM301Press (offset 404.0)
Mapeando STAT131.STAT150 -> ProcessSetup._RinsePPM303Freq (offset 408.0)
Mapeando STAT131.STAT151 -> ProcessSetup._DrainTM301Press (offset 412.0)
Mapeando STAT131.STAT152 -> ProcessSetup._KRecBlendError (offset 416.0)
Mapeando STAT131.STAT153 -> ProcessSetup._KRecCarboCO2Error (offset 420.0)
Mapeando STAT131.STAT154 -> ProcessSetup._MaxBlendError (offset 424.0)
Mapeando STAT131.STAT155 -> ProcessSetup._MaxCarboCO2Error (offset 428.0)
Mapeando STAT131.STAT156 -> ProcessSetup._StartUpBrixExtraWater (offset 432.0)
Mapeando STAT131.STAT157 -> ProcessSetup._StartUpCO2ExtraWater (offset 436.0)
Mapeando STAT131.STAT158 -> ProcessSetup._StartUpPPM303Freq (offset 440.0)
Mapeando STAT131.STAT159 -> ProcessSetup._SyrupRoomTank (offset 444.0)
Mapeando STAT131.STAT160 -> ProcessSetup._SyrupRunOutLiters (offset 446.0)
Mapeando STAT131.STAT161 -> ProcessSetup._InjCO2Press_Offset (offset 450.0)
Mapeando STAT131.STAT162 -> ProcessSetup._InjCO2Press_MinFlow (offset 454.0)
Mapeando STAT131.STAT163 -> ProcessSetup._InjCO2Press_MaxFlow (offset 458.0)
Mapeando STAT131.STAT164 -> ProcessSetup._CarboCO2Pressure (offset 462.0)
Mapeando STAT131.STAT165 -> ProcessSetup._N2MinPressure (offset 466.0)
Mapeando STAT131.STAT166 -> ProcessSetup._DiffSensor_Height (offset 470.0)
Mapeando STAT131.STAT167 -> ProcessSetup._DiffSensor_DeltaHeight (offset 474.0)
Mapeando STAT131.STAT168 -> ProcessSetup._DiffSensor_Offset (offset 478.0)
Mapeando STAT131.STAT169 -> ProcessSetup._FillingValveHeight (offset 482.0)
Mapeando STAT131.STAT170 -> ProcessSetup._FillerDiameter (offset 486.0)
Mapeando STAT131.STAT171 -> ProcessSetup._FillingValveNum (offset 490.0)
Mapeando STAT131.STAT172 -> ProcessSetup._FillerProdPipeDN (offset 492.0)
Mapeando STAT131.STAT173 -> ProcessSetup._FillerProdPipeMass (offset 496.0)
Mapeando STAT131.STAT174 -> ProcessSetup._FillingTime (offset 500.0)
Mapeando STAT131.STAT175 -> ProcessSetup._TM301Height_0 (offset 504.0)
Mapeando STAT131.STAT176 -> ProcessSetup._TM301LevelPerc_2 (offset 508.0)
Mapeando STAT131.STAT177 -> ProcessSetup._TM301Height_2 (offset 512.0)
Mapeando STAT131.STAT178 -> ProcessSetup._RVN304Factor (offset 516.0)
Mapeando STAT131.STAT179 -> ProcessSetup._DrainTM301Flushing (offset 520.0)
Mapeando STAT131.STAT180 -> ProcessSetup._FirstProdExtraBrix (offset 524.0)
Mapeando STAT131.STAT181 -> ProcessSetup._FirstProdDietExtraSyr (offset 528.0)
Mapeando STAT131.STAT182 -> ProcessSetup._EndProdLastSyrlt (offset 532.0)
Mapeando STAT131.STAT183 -> ProcessSetup._TM301DrainSt0Time (offset 536.0)
Mapeando STAT131.STAT184 -> ProcessSetup._TM301DrainSt1Time (offset 538.0)
Mapeando STAT131.STAT185 -> ProcessSetup._ProdPipeRunOutSt0Time (offset 540.0)
Mapeando STAT131.STAT186 -> ProcessSetup._RMM301ProdPipeRunOu (offset 542.0)
Mapeando STAT131.STAT187 -> ProcessSetup._RMP302ProdPipeRunOu (offset 546.0)
Mapeando STAT131.STAT188 -> ProcessSetup._ProdPipeRunOutAmount (offset 550.0)
Mapeando STAT131.STAT189 -> ProcessSetup._TM301RunOutChiller (offset 554.0)
Mapeando STAT131.STAT190 -> ProcessSetup._MinSpeedNominalProd (offset 558.0)
Mapeando STAT131.STAT191 -> ProcessSetup._MinSpeedSlowProd (offset 562.0)
Mapeando STAT131.STAT192 -> ProcessSetup._FastChgOvrTM301DrnPrss (offset 566.0)
Mapeando STAT131.STAT193 -> ProcessSetup._CIPTN301MinLevel (offset 570.0)
Mapeando STAT131.STAT194 -> ProcessSetup._CIPTN301MaxLevel (offset 574.0)
Mapeando STAT131.STAT195 -> ProcessSetup._ProdPPN304Freq (offset 578.0)
Mapeando STAT131.STAT196 -> ProcessSetup._GAS2InjectionPress (offset 582.0)
Mapeando STAT131.STAT197 -> ProcessSetup._BaialageRVM301OVMax (offset 586.0)
Mapeando STAT131.STAT198 -> ProcessSetup._RinsePPN301Freq (offset 590.0)
Mapeando STAT131.STAT199 -> ProcessSetup._CIPPPN301Freq (offset 594.0)
Mapeando STAT131.STAT200 -> ProcessSetup._RinsePPP302Freq (offset 598.0)
Mapeando STAT131.STAT201 -> ProcessSetup._CIPPPP302Freq (offset 602.0)
Mapeando STAT131.STAT202 -> ProcessSetup._PercSyrupBrixSyrStarUp (offset 606.0)
Mapeando STAT131.STAT203 -> ProcessSetup._RefTempCoolingCTRL (offset 610.0)
Mapeando STAT131.STAT204 -> ProcessSetup._H2OSerpPrimingVolume (offset 614.0)
Mapeando STAT131.STAT205 -> ProcessSetup._AVN301_Nozzle_Kv (offset 618.0)
Mapeando STAT131.STAT206 -> ProcessSetup._AVN302_Nozzle_Kv (offset 622.0)
Mapeando STAT131.STAT207 -> ProcessSetup._AVN303_Nozzle_Kv (offset 626.0)
Mapeando STAT131.STAT208 -> ProcessSetup._DeoxSpryball_Kv (offset 630.0)
Mapeando STAT131.STAT209 -> ProcessSetup._PremixedLineDrainTime (offset 634.0)
Mapeando STAT131.STAT210 -> ProcessSetup._PPN301_H_MaxFlow (offset 636.0)
Mapeando STAT131.STAT211 -> ProcessSetup._PPN301_H_MinFlow (offset 640.0)
Mapeando STAT131.STAT212 -> ProcessSetup._PPN301_MaxFlow (offset 644.0)
Mapeando STAT131.STAT213 -> ProcessSetup._PPN301_MinFlow (offset 648.0)
Mapeando STAT131.STAT214 -> ProcessSetup._PPP302_H_MaxFlow (offset 652.0)
Mapeando STAT131.STAT215 -> ProcessSetup._PPP302_H_MinFlow (offset 656.0)
Mapeando STAT131.STAT216 -> ProcessSetup._PPP302_MaxFlow (offset 660.0)
Mapeando STAT131.STAT217 -> ProcessSetup._PPP302_MinFlow (offset 664.0)
Mapeando STAT131.STAT218 -> ProcessSetup._RinsePPM306Freq (offset 668.0)
Mapeando STAT131.STAT219 -> ProcessSetup._CIPPPM306Freq (offset 672.0)
Mapeando STAT131.STAT220 -> ProcessSetup._PPM307_H_MaxFlow (offset 676.0)
Mapeando STAT131.STAT221 -> ProcessSetup._PPM307_H_MinFlow (offset 680.0)
Mapeando STAT131.STAT222 -> ProcessSetup._PPM307_MaxFlow (offset 684.0)
Mapeando STAT131.STAT223 -> ProcessSetup._PPM307_MinFlow (offset 688.0)
Mapeando STAT131.STAT224 -> ProcessSetup._Temp0_VacuumCtrl (offset 692.0)
Mapeando STAT131.STAT225 -> ProcessSetup._Temp1_VacuumCtrl (offset 696.0)
Mapeando STAT131.STAT226 -> ProcessSetup._Temp2_VacuumCtrl (offset 700.0)
Mapeando STAT131.STAT227 -> ProcessSetup._Temp3_VacuumCtrl (offset 704.0)
Mapeando STAT131.STAT228 -> ProcessSetup._Temp4_VacuumCtrl (offset 708.0)
Mapeando STAT131.STAT229 -> ProcessSetup._T1_VacuumCtrl (offset 712.0)
Mapeando STAT131.STAT230 -> ProcessSetup._T2_VacuumCtrl (offset 716.0)
Mapeando STAT131.STAT231 -> ProcessSetup._T3_VacuumCtrl (offset 720.0)
Mapeando STAT131.STAT232 -> ProcessSetup._T4_VacuumCtrl (offset 724.0)
Mapeando STAT131.STAT233 -> ProcessSetup._ICS_VolDosWorkTimePAA (offset 728.0)
Mapeando STAT131.STAT234 -> ProcessSetup._ICS_VolPauseTimePAA (offset 730.0)
Mapeando STAT131.STAT235 -> ProcessSetup._ICS_PAAPulseWeight (offset 732.0)
Mapeando STAT131.STAT236 -> ProcessSetup._ICS_CausticPulseWeight (offset 734.0)
Mapeando STAT131.STAT237 -> ProcessSetup._ICS_AcidPulseWeight (offset 736.0)
Mapeando STAT131.STAT238 -> ProcessSetup._ICS_VolumeRestOfLine (offset 738.0)
Mapeando STAT131.STAT239 -> ProcessSetup._ICS_VolDosWorkTimeCaus (offset 742.0)
Mapeando STAT131.STAT240 -> ProcessSetup._ICS_VolDosPauseTimeCaus (offset 744.0)
Mapeando STAT131.STAT241 -> ProcessSetup._ICS_VolDosWorkTimeAcid (offset 746.0)
Mapeando STAT131.STAT242 -> ProcessSetup._ICS_VolDosPauseTimeAcid (offset 748.0)
Mapeando STAT131.STAT243 -> ProcessSetup._ICS_ConcDosWorkTimeCaus (offset 750.0)
Mapeando STAT131.STAT244 -> ProcessSetup._ICS_ConcDosPausTimeCaus (offset 752.0)
Mapeando STAT131.STAT245 -> ProcessSetup._ICS_ConcDosWorkTimeAcid (offset 754.0)
Mapeando STAT131.STAT246 -> ProcessSetup._ICS_ConcDosPausTimeAcid (offset 756.0)
Mapeando STAT131.STAT247 -> ProcessSetup._RinsePPM307Freq (offset 758.0)
Mapeando STAT131.STAT248 -> ProcessSetup._CIPPPM307Freq (offset 762.0)
Mapeando STAT131.STAT249 -> ProcessSetup._CIP2StepTN301Lvl (offset 766.0)
Mapeando STAT131.STAT250 -> ProcessSetup._CIP2StepTM301Lvl (offset 770.0)
Mapeando STAT131.STAT251 -> ProcessSetup._CIP2StepTP301Lvl (offset 774.0)
Mapeando STAT131.STAT252 -> ProcessSetup._PumpNominalFreq (offset 778.0)
Mapeando STAT253 -> _SwitchOff_DensityOK (offset 782.0)
Mapeando STAT254 -> STAT254 (offset 784.0)
Archivo _updated generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json\db1001_updated.json
--- Proceso completado ---
--- ERRORES (STDERR) ---
Ninguno

View File

@ -1,413 +1,393 @@
# --- x7.py ---
import json
import os
import sys
import glob
import sys
import copy
import re
from typing import List, Dict, Optional, Tuple, Any
from typing import Dict, List, Tuple, Any, Optional
# Assuming x3.py and x4.py are in the same directory or accessible via PYTHONPATH
# Imports from x3.py
from x3 import (
S7Parser,
ParsedData, # Dataclass for top-level structure
# The following dataclasses are defined in x3.py and used by S7Parser.
# We might not need to import them explicitly if we work with dicts from JSON.
# VariableInfo, ArrayDimension, UdtInfo, DbInfo,
custom_json_serializer,
find_working_directory,
# Importar load_configuration desde backend.script_utils
script_root = os.path.dirname(
os.path.dirname(os.path.dirname(os.path.dirname(__file__)))
)
sys.path.append(script_root)
from backend.script_utils import load_configuration
# Imports from x4.py (or reimplementations if direct import is problematic)
# These functions from x4.py work on dictionary representations of the parsed data.
from x4 import (
format_data_type_for_source,
generate_variable_declaration_for_source,
generate_struct_members_for_source,
generate_begin_block_assignments,
generate_s7_source_code_lines,
)
# Importar lo necesario desde x3.py
sys.path.append(os.path.dirname(__file__))
from x3 import S7Parser, find_working_directory, custom_json_serializer, ParsedData
# --- Helper Functions ---
def find_data_format_files(working_dir: str) -> Tuple[Optional[str], Optional[str]]:
"""Finds _data and _format files in the working directory."""
data_file: Optional[str] = None
format_file: Optional[str] = None
extensions = ["*.db", "*.awl", "*.db.txt", "*.awl.txt"]
all_s7_files = []
for ext_pattern in extensions:
all_s7_files.extend(glob.glob(os.path.join(working_dir, ext_pattern)))
# Prioritize longer extensions first for matching to avoid partial matches like .db when .db.txt exists
all_s7_files.sort(key=len, reverse=True)
for f_path in all_s7_files:
basename = os.path.basename(f_path)
# Check for _data file (and ensure it's not an _updated file from a previous run)
if "_data" in basename and "_updated" not in basename:
# More specific check to avoid matching e.g. "some_other_data_related_file"
# We expect "PREFIX_data.EXT"
name_part, _ = os.path.splitext(
basename
) # For "file.db.txt", this gives "file.db"
if name_part.endswith("_data") or basename.replace(
os.path.splitext(basename)[-1], ""
).endswith(
"_data"
): # Handles single and double extensions
if data_file is None: # Take the first one found (after sorting)
data_file = f_path
# Check for _format file
if "_format" in basename and "_updated" not in basename:
name_part, _ = os.path.splitext(basename)
if name_part.endswith("_format") or basename.replace(
os.path.splitext(basename)[-1], ""
).endswith("_format"):
if format_file is None:
format_file = f_path
if data_file:
print(f"Found _data file: {data_file}")
else:
print("Warning: No _data file found.")
if format_file:
print(f"Found _format file: {format_file}")
else:
print("Warning: No _format file found.")
return data_file, format_file
def parse_s7_to_json_file(s7_filepath: str, json_dir: str) -> Optional[str]:
"""Parses an S7 source file to JSON and saves it."""
parser = S7Parser()
filename = os.path.basename(s7_filepath)
print(f"Parsing S7 file: {filename}...")
try:
parsed_result = parser.parse_file(s7_filepath)
except Exception as e:
print(f"Error parsing {filename}: {e}")
return None
output_filename_base = os.path.splitext(filename)[0]
# Handle double extensions like .db.txt
if ".db" in output_filename_base or ".awl" in output_filename_base:
# A more robust way to get the true base name before multiple extensions
# Example: "file.db.txt" -> "file"
# Example: "file.db" -> "file"
temp_name = filename
known_exts = [
".txt",
".db",
".awl",
] # order might matter if extensions can be part of name
for k_ext in reversed(known_exts): # try removing from right to left
if temp_name.lower().endswith(k_ext):
temp_name = temp_name[: -len(k_ext)]
output_filename_base = temp_name # This is the "true" base
json_output_filename = os.path.join(
json_dir,
f"{output_filename_base}_{os.path.basename(s7_filepath).split('_', 1)[1].split('.')[0]}.json",
) # e.g. base_data.json
print(f"Serializing to JSON: {json_output_filename}")
try:
json_output = json.dumps(
parsed_result, default=custom_json_serializer, indent=2
)
with open(json_output_filename, "w", encoding="utf-8") as f:
f.write(json_output)
print(f"JSON saved: {json_output_filename}")
return json_output_filename
except Exception as e:
print(f"Error during JSON serialization or writing for {filename}: {e}")
return None
def load_json_file(json_filepath: str) -> Optional[Dict[str, Any]]:
"""Loads a JSON file into a Python dictionary."""
try:
with open(json_filepath, "r", encoding="utf-8") as f:
data = json.load(f)
return data
except Exception as e:
print(f"Error loading JSON file {json_filepath}: {e}")
return None
def flatten_db_variables_for_compare(
members_list: List[Dict[str, Any]], parent_path: str = ""
) -> List[Tuple[str, Dict[str, Any]]]:
def find_matching_files(working_dir: str) -> List[Tuple[str, str]]:
"""
Flattens DB members for comparison.
Collects all 'leaf' nodes (primitives, arrays of primitives, strings)
and their full paths.
Busca pares de archivos _data y _format con extensión .db o .awl.
"""
flat_list = []
for var_info in members_list:
var_name_segment = var_info["name"]
current_var_path = (
f"{parent_path}{var_name_segment}" if parent_path else var_name_segment
)
# Buscar archivos _data
data_files_db = glob.glob(os.path.join(working_dir, "*_data.db"))
data_files_awl = glob.glob(os.path.join(working_dir, "*_data.awl"))
all_data_files = data_files_db + data_files_awl
if var_info.get("children"):
flat_list.extend(
flatten_db_variables_for_compare(
var_info["children"], f"{current_var_path}."
)
)
else:
flat_list.append((current_var_path, var_info))
return flat_list
# Buscar archivos _format
format_files_db = glob.glob(os.path.join(working_dir, "*_format.db"))
format_files_awl = glob.glob(os.path.join(working_dir, "*_format.awl"))
all_format_files = format_files_db + format_files_awl
# Emparejar archivos _data y _format
matched_pairs = []
for data_file in all_data_files:
base_name = os.path.basename(data_file).replace("_data", "").split('.')[0]
format_candidates = [f for f in all_format_files if os.path.basename(f).startswith(f"{base_name}_format")]
if format_candidates:
matched_pairs.append((data_file, format_candidates[0]))
def compare_db_structures(data_db: Dict[str, Any], format_db: Dict[str, Any]) -> bool:
return matched_pairs
def parse_files_to_json(data_file: str, format_file: str, json_dir: str) -> Tuple[Dict, Dict]:
"""
Compares the structure of two DBs (as dicts from JSON).
Returns True if compatible, False otherwise.
Parsea los archivos _data y _format usando S7Parser y guarda los resultados como JSON.
"""
db_name = format_db.get("name", "UnknownDB")
print(f"Comparing structure of DB: {db_name}")
# Instancias separadas del parser para cada archivo
data_parser = S7Parser()
format_parser = S7Parser()
flat_data_vars_with_paths = flatten_db_variables_for_compare(
data_db.get("members", [])
)
flat_format_vars_with_paths = flatten_db_variables_for_compare(
format_db.get("members", [])
)
print(f"Parseando archivo data: {os.path.basename(data_file)}")
data_result = data_parser.parse_file(data_file)
if len(flat_data_vars_with_paths) != len(flat_format_vars_with_paths):
print(f"Error: DB '{db_name}' tiene un número diferente de variables expandidas (hoja).")
print(f" Número de variables en archivo _data: {len(flat_data_vars_with_paths)}")
print(f" Número de variables en archivo _format: {len(flat_format_vars_with_paths)}")
print(f"Parseando archivo format: {os.path.basename(format_file)}")
format_result = format_parser.parse_file(format_file)
min_len = min(len(flat_data_vars_with_paths), len(flat_format_vars_with_paths))
divergence_found_early = False
# Revisar si hay un tipo de dato o nombre diferente antes del final de la lista más corta
for k in range(min_len):
path_data_k, var_data_k = flat_data_vars_with_paths[k]
path_format_k, var_format_k = flat_format_vars_with_paths[k]
# Guardar resultados como JSON
data_base = os.path.splitext(os.path.basename(data_file))[0]
format_base = os.path.splitext(os.path.basename(format_file))[0]
type_str_data_k = format_data_type_for_source(var_data_k)
type_str_format_k = format_data_type_for_source(var_format_k)
data_json_path = os.path.join(json_dir, f"{data_base}.json")
format_json_path = os.path.join(json_dir, f"{format_base}.json")
# Comparamos tipos. Los nombres pueden diferir si la estructura interna de un UDT/Struct cambió.
# La ruta del _data es aproximada si los nombres de los miembros de structs/UDTs cambiaron.
if type_str_data_k != type_str_format_k:
print(f" Adicionalmente, se encontró una discrepancia de tipo ANTES del final de la lista más corta (índice {k}):")
print(f" _format variable: Path='{path_format_k}', Nombre='{var_format_k['name']}', Tipo='{type_str_format_k}'")
print(f" _data variable: Path='{path_data_k}' (aprox.), Nombre='{var_data_k['name']}', Tipo='{type_str_data_k}'")
divergence_found_early = True
break
# Serializar y guardar como JSON
data_json = json.dumps(data_result, default=custom_json_serializer, indent=2)
format_json = json.dumps(format_result, default=custom_json_serializer, indent=2)
if not divergence_found_early:
# Si no hubo discrepancias tempranas, la diferencia es por variables extra al final.
if len(flat_data_vars_with_paths) > len(flat_format_vars_with_paths):
print(f" El archivo _data tiene {len(flat_data_vars_with_paths) - min_len} variable(s) más.")
print(f" Primeras variables extra en _data (path, nombre, tipo) desde el índice {min_len}:")
for j in range(min_len, min(min_len + 5, len(flat_data_vars_with_paths))): # Mostrar hasta 5 extra
path, var = flat_data_vars_with_paths[j]
print(f" - Path: '{path}', Nombre: '{var['name']}', Tipo: '{format_data_type_for_source(var)}'")
else:
print(f" El archivo _format tiene {len(flat_format_vars_with_paths) - min_len} variable(s) más.")
print(f" Primeras variables extra en _format (path, nombre, tipo) desde el índice {min_len}:")
for j in range(min_len, min(min_len + 5, len(flat_format_vars_with_paths))): # Mostrar hasta 5 extra
path, var = flat_format_vars_with_paths[j]
print(f" - Path: '{path}', Nombre: '{var['name']}', Tipo: '{format_data_type_for_source(var)}'")
return False
with open(data_json_path, "w", encoding='utf-8') as f:
f.write(data_json)
for i in range(len(flat_format_vars_with_paths)):
path_data, var_data = flat_data_vars_with_paths[i]
path_format, var_format = flat_format_vars_with_paths[i]
with open(format_json_path, "w", encoding='utf-8') as f:
f.write(format_json)
type_str_data = format_data_type_for_source(var_data)
type_str_format = format_data_type_for_source(var_format)
print(f"Archivos JSON generados: {os.path.basename(data_json_path)} y {os.path.basename(format_json_path)}")
if type_str_data != type_str_format:
print(f"Error: Discrepancia de tipo en DB '{db_name}' para la variable en el índice {i} (contando desde 0) de la lista expandida.")
print(f" Comparando:")
print(f" _format variable: Path='{path_format}', Nombre='{var_format['name']}', Tipo Declarado='{type_str_format}'")
print(f" Offset: {var_format.get('byte_offset')}, Tamaño: {var_format.get('size_in_bytes')} bytes")
print(f" _data variable: Path='{path_data}' (aprox.), Nombre='{var_data['name']}', Tipo Declarado='{type_str_data}'")
print(f" Offset: {var_data.get('byte_offset')}, Tamaño: {var_data.get('size_in_bytes')} bytes")
return False
# Cargar de nuevo como objetos para procesamiento
data_obj = json.loads(data_json)
format_obj = json.loads(format_json)
print(f"La estructura del DB '{db_name}' es compatible.")
return True
return data_obj, format_obj
def update_format_db_members_recursive(
format_members: List[Dict[str, Any]], data_members: List[Dict[str, Any]]
):
def create_offset_path_map(members: List[Dict], path_prefix: str = "") -> Dict[float, str]:
"""
Recursively updates 'initial_value', 'current_value', and 'current_element_values'
in format_members using values from data_members.
Assumes structures are compatible and lists have the same length.
Crea un mapa que asocia cada offset con la ruta completa de la variable.
Esto será usado para actualizar las asignaciones del bloque BEGIN.
"""
for i in range(len(format_members)):
fm_var = format_members[i]
dm_var = data_members[i]
offset_to_path = {}
fm_var["initial_value"] = dm_var.get("initial_value")
fm_var["current_value"] = dm_var.get("current_value")
if "current_element_values" in dm_var:
fm_var["current_element_values"] = dm_var["current_element_values"]
elif "current_element_values" in fm_var:
del fm_var["current_element_values"]
def process_member(member: Dict, current_path_prefix: str):
offset = member["byte_offset"]
full_path = f"{current_path_prefix}{member['name']}"
if fm_var.get("children") and dm_var.get("children"):
if len(fm_var["children"]) == len(dm_var["children"]):
update_format_db_members_recursive(
fm_var["children"], dm_var["children"]
)
else:
print(
f"Warning: Mismatch in children count for {fm_var['name']} during update. This is unexpected."
)
# Mapear offset a ruta completa
offset_to_path[offset] = full_path
# Procesar hijos recursivamente
if "children" in member and member["children"]:
for child in member["children"]:
process_member(child, f"{full_path}.")
def get_updated_filename(format_filename_basename: str) -> str:
"""Generates the output filename for the _updated file."""
suffixes_map = {
"_format.db.txt": "_updated.db.txt",
"_format.awl.txt": "_updated.awl.txt",
"_format.db": "_updated.db",
"_format.awl": "_updated.awl",
# Procesar todos los miembros
for member in members:
process_member(member, path_prefix)
return offset_to_path
def flatten_variables_by_offset(data: Dict) -> Dict[float, Dict]:
"""
Aplana completamente todas las variables por offset, similar a flatten_members_for_markdown.
Incluye UDTs expandidos, estructuras anidadas, etc.
"""
offset_map = {}
processed_expanded_members = set()
def process_members(members: List[Dict], prefix: str = "", is_expansion: bool = False):
for var_idx, var in enumerate(members):
# Control para miembros UDT expandidos (evitar duplicados)
member_id = f"{prefix}{var['name']}_{var_idx}"
if is_expansion and member_id in processed_expanded_members:
continue
if is_expansion:
processed_expanded_members.add(member_id)
# Extraer offset e información de la variable
offset = var["byte_offset"]
var_info = {
"path": f"{prefix}{var['name']}",
"data_type": var["data_type"],
"size_in_bytes": var["size_in_bytes"],
"bit_size": var.get("bit_size", 0),
"initial_value": var.get("initial_value"),
"current_value": var.get("current_value"),
"current_element_values": var.get("current_element_values")
}
for s_format, s_updated in suffixes_map.items():
if format_filename_basename.lower().endswith(s_format.lower()):
base = format_filename_basename[: -len(s_format)]
return base + s_updated
# Guardar en mapa por offset
offset_map[offset] = var_info
if "_format" in format_filename_basename:
return format_filename_basename.replace("_format", "_updated")
# Procesar recursivamente los hijos
if "children" in var and var["children"]:
process_members(
var["children"],
f"{prefix}{var['name']}.",
is_expansion=bool(var.get("udt_source_name"))
)
name, ext = os.path.splitext(format_filename_basename)
return f"{name}_updated{ext}"
# Procesar todos los DBs
for db in data.get("dbs", []):
process_members(db.get("members", []))
return offset_map
def create_path_to_offset_map(members: List[Dict], path_prefix: str = "") -> Dict[str, float]:
"""
Crea un mapa que asocia cada ruta (path) completa con su offset.
Esto será usado para actualizar las asignaciones del bloque BEGIN.
"""
path_to_offset = {}
processed_expanded_members = set()
def process_member(member: Dict, current_path_prefix: str, is_expansion: bool = False):
member_id = f"{current_path_prefix}{member['name']}"
# Evitar duplicados para miembros expandidos de UDTs
if is_expansion and member_id in processed_expanded_members:
return
if is_expansion:
processed_expanded_members.add(member_id)
offset = member["byte_offset"]
path = f"{current_path_prefix}{member['name']}"
# Mapear ruta a offset
path_to_offset[path] = offset
# Para arrays, también mapear rutas con índices si hay valores iniciales
if member.get("array_dimensions") and member.get("current_element_values"):
for index in member["current_element_values"].keys():
array_path = f"{path}[{index}]"
path_to_offset[array_path] = offset
# Procesar hijos recursivamente
if "children" in member and member["children"]:
for child in member["children"]:
process_member(
child,
f"{path}.",
is_expansion=bool(member.get("udt_source_name"))
)
# Procesar todos los miembros
for member in members:
process_member(member, path_prefix)
return path_to_offset
def compare_structures_by_offset(data_vars: Dict[float, Dict], format_vars: Dict[float, Dict]) -> Tuple[bool, List[str]]:
"""
Compara variables por offset, verificando compatibilidad.
"""
issues = []
# Recopilar todos los offsets únicos de ambos conjuntos
all_offsets = sorted(set(list(data_vars.keys()) + list(format_vars.keys())))
# Verificar que todos los offsets existan en ambos conjuntos
for offset in all_offsets:
if offset not in data_vars:
issues.append(f"Offset {offset} existe en _format pero no en _data")
continue
if offset not in format_vars:
issues.append(f"Offset {offset} existe en _data pero no en _format")
continue
# Verificar coincidencia de tipos
data_type = data_vars[offset]["data_type"].upper()
format_type = format_vars[offset]["data_type"].upper()
if data_type != format_type:
issues.append(f"Tipo de dato diferente en offset {offset}: {data_type} ({data_vars[offset]['path']}) vs {format_type} ({format_vars[offset]['path']})")
# Verificar tamaño
data_size = data_vars[offset]["size_in_bytes"]
format_size = format_vars[offset]["size_in_bytes"]
if data_size != format_size:
issues.append(f"Tamaño diferente en offset {offset}: {data_size} bytes ({data_vars[offset]['path']}) vs {format_size} bytes ({format_vars[offset]['path']})")
# Verificar tamaño en bits para BOOLs
data_bit_size = data_vars[offset]["bit_size"]
format_bit_size = format_vars[offset]["bit_size"]
if data_bit_size != format_bit_size:
issues.append(f"Tamaño en bits diferente en offset {offset}: {data_bit_size} ({data_vars[offset]['path']}) vs {format_bit_size} ({format_vars[offset]['path']})")
return len(issues) == 0, issues
def update_values_recursive(target_member: Dict, data_offset_map: Dict[float, Dict]):
"""
Actualiza los valores de target_member con valores de data_offset_map basado en offset.
"""
offset = target_member["byte_offset"]
# Si encontramos una variable con el mismo offset en _data, tomar sus valores
if offset in data_offset_map:
data_var = data_offset_map[offset]
# Actualizar initial_value
if "initial_value" in data_var and data_var["initial_value"] is not None:
target_member["initial_value"] = data_var["initial_value"]
# Actualizar current_value
if "current_value" in data_var and data_var["current_value"] is not None:
target_member["current_value"] = data_var["current_value"]
# Actualizar current_element_values (para arrays)
if "current_element_values" in data_var and data_var["current_element_values"]:
target_member["current_element_values"] = data_var["current_element_values"]
# Actualizar recursivamente los hijos
if "children" in target_member and target_member["children"]:
for child in target_member["children"]:
update_values_recursive(child, data_offset_map)
def create_updated_json(data_json: Dict, format_json: Dict) -> Dict:
"""
Crea JSON actualizado basado en la estructura de _format con valores de _data.
"""
# Copia profunda de format_json para no modificar el original
updated_json = copy.deepcopy(format_json)
# Extraer todas las variables flat por offset
data_offset_map = flatten_variables_by_offset(data_json)
# Crear mapas de offsets y rutas para cada BD
db_maps = {}
for db_idx, db in enumerate(format_json.get("dbs", [])):
db_name = db["name"]
db_maps[db_name] = {
"offset_to_path": create_offset_path_map(db.get("members", [])),
"path_to_offset": create_path_to_offset_map(db.get("members", []))
}
# Actualizar valores de variables en la estructura de formato
for db_idx, db in enumerate(updated_json.get("dbs", [])):
for member in db.get("members", []):
update_values_recursive(member, data_offset_map)
# Actualizar también asignaciones del bloque BEGIN
db_name = db["name"]
data_db = next((d for d in data_json.get("dbs", []) if d["name"] == db_name), None)
if data_db and "_begin_block_assignments_ordered" in data_db:
# Obtener los mapas para este DB
offset_to_path = db_maps[db_name]["offset_to_path"]
# Crear una nueva lista de asignaciones con las rutas correctas
updated_assignments = []
# Para cada asignación en los datos de origen
for path, value in data_db["_begin_block_assignments_ordered"]:
# Búsqueda por offset si es posible
data_db_path_to_offset = create_path_to_offset_map(data_db.get("members", []))
if path in data_db_path_to_offset:
# Obtener el offset de la ruta original
offset = data_db_path_to_offset[path]
# Buscar la ruta correspondiente en el formato usando el offset
if offset in offset_to_path:
new_path = offset_to_path[offset]
updated_assignments.append([new_path, value])
print(f"Mapeando {path} -> {new_path} (offset {offset})")
else:
print(f"Advertencia: No se encontró un mapeo para el offset {offset} ({path})")
else:
print(f"Advertencia: No se pudo determinar el offset para la ruta {path}")
# Actualizar asignaciones en el JSON actualizado
db["_begin_block_assignments_ordered"] = updated_assignments
# También actualizar el diccionario _initial_values_from_begin_block
if "_initial_values_from_begin_block" in data_db:
updated_values = {}
for path, value in updated_assignments:
updated_values[path] = value
db["_initial_values_from_begin_block"] = updated_values
return updated_json
# --- Main Script Logic ---
def main():
# Obtener directorio de trabajo
working_dir = find_working_directory()
print(f"Using working directory: {working_dir}")
data_s7_filepath, format_s7_filepath = find_data_format_files(working_dir)
# Crear directorio para JSON si no existe
output_json_dir = os.path.join(working_dir, "json")
os.makedirs(output_json_dir, exist_ok=True)
print(f"Los archivos JSON se guardarán en: {output_json_dir}")
if not data_s7_filepath or not format_s7_filepath:
print(
"Error: Both _data and _format S7 source files must be present. Aborting."
)
# Buscar pares de archivos _data y _format
matched_pairs = find_matching_files(working_dir)
if not matched_pairs:
print("No se encontraron pares de archivos _data y _format para procesar.")
return
json_dir = os.path.join(working_dir, "json")
os.makedirs(json_dir, exist_ok=True)
print(f"Se encontraron {len(matched_pairs)} pares de archivos para procesar.")
data_json_filepath = parse_s7_to_json_file(data_s7_filepath, json_dir)
if not data_json_filepath:
print("Failed to parse _data file. Aborting.")
return
data_parsed_dict = load_json_file(data_json_filepath)
if not data_parsed_dict:
print("Failed to load _data JSON. Aborting.")
return
for data_file, format_file in matched_pairs:
print(f"\n--- Procesando par de archivos ---")
print(f"Data file: {os.path.basename(data_file)}")
print(f"Format file: {os.path.basename(format_file)}")
format_json_filepath = parse_s7_to_json_file(format_s7_filepath, json_dir)
if not format_json_filepath:
print("Failed to parse _format file. Aborting.")
return
format_parsed_dict = load_json_file(format_json_filepath)
if not format_parsed_dict:
print("Failed to load _format JSON. Aborting.")
return
# Parsear archivos a JSON
data_json, format_json = parse_files_to_json(data_file, format_file, output_json_dir)
data_dbs = data_parsed_dict.get("dbs", [])
format_dbs = format_parsed_dict.get("dbs", [])
# Aplanar variables por offset
print("Aplanando variables por offset...")
data_offset_map = flatten_variables_by_offset(data_json)
format_offset_map = flatten_variables_by_offset(format_json)
if not format_dbs:
print("No Data Blocks found in the _format file. Nothing to update. Aborting.")
return
# Comparar estructuras usando offset como clave
print(f"Comparando estructuras: {len(data_offset_map)} variables en _data, {len(format_offset_map)} variables en _format")
compatible, issues = compare_structures_by_offset(data_offset_map, format_offset_map)
if len(data_dbs) != len(format_dbs):
print(
f"Error: Mismatch in the number of Data Blocks. "
f"_data file has {len(data_dbs)} DBs, _format file has {len(format_dbs)} DBs. Aborting."
)
return
if not compatible:
print("\nSe encontraron problemas de compatibilidad entre los archivos:")
for issue in issues:
print(f" - {issue}")
print("\nAbortando el proceso para este par de archivos.")
continue
all_dbs_compatible = True
for i in range(len(format_dbs)):
current_format_db = format_dbs[i]
current_data_db = next(
(db for db in data_dbs if db["name"] == current_format_db["name"]), None
)
print("\nLos archivos son compatibles. Creando el archivo _updated...")
if not current_data_db:
print(
f"Error: DB '{current_format_db['name']}' from _format file not found in _data file. Aborting."
)
all_dbs_compatible = False
break
# Crear JSON actualizado usando el mapa de offsets de _data
updated_json = create_updated_json(data_json, format_json)
if not compare_db_structures(current_data_db, current_format_db):
all_dbs_compatible = False
break
# Guardar la versión actualizada
base_name = os.path.basename(format_file).replace("_format", "").split('.')[0]
updated_json_path = os.path.join(output_json_dir, f"{base_name}_updated.json")
if not all_dbs_compatible:
print("Comparison failed. Aborting generation of _updated file.")
return
with open(updated_json_path, "w", encoding='utf-8') as f:
json.dump(updated_json, f, default=custom_json_serializer, indent=2)
print("\nAll DB structures are compatible. Proceeding to generate _updated file.")
updated_parsed_dict = copy.deepcopy(format_parsed_dict)
updated_parsed_dict["udts"] = format_parsed_dict.get("udts", [])
updated_dbs_list = updated_parsed_dict.get("dbs", [])
for i in range(len(updated_dbs_list)):
updated_db_ref = updated_dbs_list[i]
data_db_original = next(
(db for db in data_dbs if db["name"] == updated_db_ref["name"]), None
)
if not data_db_original:
print(
f"Critical Error: Could not find data DB {updated_db_ref['name']} during update phase. Aborting."
)
return
if "members" in updated_db_ref and "members" in data_db_original:
update_format_db_members_recursive(
updated_db_ref["members"], data_db_original["members"]
)
updated_db_ref["_begin_block_assignments_ordered"] = data_db_original.get(
"_begin_block_assignments_ordered", []
)
updated_db_ref["_initial_values_from_begin_block"] = data_db_original.get(
"_initial_values_from_begin_block", {}
)
s7_output_lines = generate_s7_source_code_lines(updated_parsed_dict)
output_s7_filename_basename = get_updated_filename(
os.path.basename(format_s7_filepath)
)
output_s7_filepath = os.path.join(working_dir, output_s7_filename_basename)
try:
with open(output_s7_filepath, "w", encoding="utf-8") as f:
for line in s7_output_lines:
f.write(line + "\n")
print(f"\nSuccessfully generated _updated S7 file: {output_s7_filepath}")
except Exception as e:
print(f"Error writing _updated S7 file {output_s7_filepath}: {e}")
print(f"Archivo _updated generado: {updated_json_path}")
print("\n--- Proceso completado ---")
if __name__ == "__main__":
main()

View File

@ -1,17 +1,319 @@
[23:48:43] Iniciando ejecución de x7_value_updater.py en C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001...
[23:48:43] Using working directory: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001
[23:48:43] Found _data file: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\db1001_data.db
[23:48:43] Found _format file: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\db1001_format.db
[23:48:43] Parsing S7 file: db1001_data.db...
[23:48:43] Serializing to JSON: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json\db1001_data_data.json
[23:48:43] JSON saved: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json\db1001_data_data.json
[23:48:43] Parsing S7 file: db1001_format.db...
[23:48:43] Serializing to JSON: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json\db1001_format_format.json
[23:48:43] JSON saved: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json\db1001_format_format.json
[23:48:43] Comparing structure of DB: HMI_Blender_Parameters
[23:48:43] La estructura del DB 'HMI_Blender_Parameters' es compatible.
[23:48:43] All DB structures are compatible. Proceeding to generate _updated file.
[23:48:43] INFO: Usando '_begin_block_assignments_ordered' para generar bloque BEGIN de DB 'HMI_Blender_Parameters'.
[23:48:43] Successfully generated _updated S7 file: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\db1001_updated.db
[23:48:43] Ejecución de x7_value_updater.py finalizada (success). Duración: 0:00:00.106052.
[23:48:43] Log completo guardado en: D:\Proyectos\Scripts\ParamManagerScripts\backend\script_groups\S7_DB_Utils\log_x7_value_updater.txt
[00:51:17] Iniciando ejecución de x7_value_updater.py en C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001...
[00:51:18] Using working directory: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001
[00:51:18] Los archivos JSON se guardarán en: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json
[00:51:18] Se encontraron 1 pares de archivos para procesar.
[00:51:18] --- Procesando par de archivos ---
[00:51:18] Data file: db1001_data.db
[00:51:18] Format file: db1001_format.db
[00:51:18] Parseando archivo data: db1001_data.db
[00:51:18] Parseando archivo format: db1001_format.db
[00:51:18] Archivos JSON generados: db1001_data.json y db1001_format.json
[00:51:18] Aplanando variables por offset...
[00:51:18] Comparando estructuras: 251 variables en _data, 251 variables en _format
[00:51:18] Los archivos son compatibles. Creando el archivo _updated...
[00:51:18] Mapeando STAT0.STAT1.STAT2 -> Processor_Options.Blender_OPT._ModelNum (offset 0.0)
[00:51:18] Mapeando STAT0.STAT1.STAT3 -> Processor_Options.Blender_OPT._CO2_Offset (offset 2.0)
[00:51:18] Mapeando STAT0.STAT1.STAT4 -> Processor_Options.Blender_OPT._MaxSyrDeltaBrix (offset 6.0)
[00:51:18] Mapeando STAT0.STAT1.STAT5 -> Processor_Options.Blender_OPT._BrixMeter (offset 10.0)
[00:51:18] Mapeando STAT0.STAT1.STAT6 -> Processor_Options.Blender_OPT.Spare101 (offset 10.1)
[00:51:18] Mapeando STAT0.STAT1.STAT7 -> Processor_Options.Blender_OPT._TrackH2OEnable (offset 10.2)
[00:51:18] Mapeando STAT0.STAT1.STAT8 -> Processor_Options.Blender_OPT._PAmPDSType (offset 10.3)
[00:51:18] Mapeando STAT0.STAT1.STAT9 -> Processor_Options.Blender_OPT._HistoricalTrends (offset 10.4)
[00:51:18] Mapeando STAT0.STAT1.STAT10 -> Processor_Options.Blender_OPT._PowerMeter (offset 10.5)
[00:51:18] Mapeando STAT0.STAT1.STAT11 -> Processor_Options.Blender_OPT._Report (offset 10.6)
[00:51:18] Mapeando STAT0.STAT1.STAT12 -> Processor_Options.Blender_OPT._Balaiage (offset 10.7)
[00:51:18] Mapeando STAT0.STAT1.STAT13 -> Processor_Options.Blender_OPT._Valves_FullFeedback (offset 11.0)
[00:51:18] Mapeando STAT0.STAT1.STAT14 -> Processor_Options.Blender_OPT._Valves_SingleFeedback (offset 11.1)
[00:51:18] Mapeando STAT0.STAT1.STAT15 -> Processor_Options.Blender_OPT._PumpsSafetySwitches (offset 11.2)
[00:51:18] Mapeando STAT0.STAT1.STAT16 -> Processor_Options.Blender_OPT._SurgeProtectionAct (offset 11.3)
[00:51:18] Mapeando STAT0.STAT1.STAT17 -> Processor_Options.Blender_OPT._DBC_Type (offset 11.4)
[00:51:18] Mapeando STAT0.STAT1.STAT18 -> Processor_Options.Blender_OPT._CO2InletMeter (offset 11.5)
[00:51:18] Mapeando STAT0.STAT1.STAT19 -> Processor_Options.Blender_OPT._ProductO2Meter (offset 11.6)
[00:51:18] Mapeando STAT0.STAT1.STAT20 -> Processor_Options.Blender_OPT._CopressedAirInletMeter (offset 11.7)
[00:51:18] Mapeando STAT0.STAT1.STAT21 -> Processor_Options.Blender_OPT._MeterType (offset 12.0)
[00:51:18] Mapeando STAT0.STAT1.STAT22 -> Processor_Options.Blender_OPT._MeterReceiveOnly (offset 14.0)
[00:51:18] Mapeando STAT0.STAT1.STAT23 -> Processor_Options.Blender_OPT._SyrBrixMeter (offset 14.1)
[00:51:18] Mapeando STAT0.STAT1.STAT24 -> Processor_Options.Blender_OPT._Flooding_Start_Up (offset 14.2)
[00:51:18] Mapeando STAT0.STAT1.STAT25 -> Processor_Options.Blender_OPT._FastChangeOverEnabled (offset 14.3)
[00:51:18] Mapeando STAT0.STAT1.STAT26 -> Processor_Options.Blender_OPT._WaterInletMeter (offset 14.4)
[00:51:18] Mapeando STAT0.STAT1.STAT27 -> Processor_Options.Blender_OPT._BlendFillSystem (offset 14.5)
[00:51:18] Mapeando STAT0.STAT1.STAT28 -> Processor_Options.Blender_OPT._TrackFillerSpeed (offset 14.6)
[00:51:18] Mapeando STAT0.STAT1.STAT29 -> Processor_Options.Blender_OPT._SignalExchange (offset 16.0)
[00:51:18] Mapeando STAT0.STAT1.STAT30 -> Processor_Options.Blender_OPT._CoolerPresent (offset 18.0)
[00:51:18] Mapeando STAT0.STAT1.STAT31 -> Processor_Options.Blender_OPT._CoolerControl (offset 20.0)
[00:51:18] Mapeando STAT0.STAT1.STAT32 -> Processor_Options.Blender_OPT._CoolerType (offset 22.0)
[00:51:18] Mapeando STAT0.STAT1.STAT33 -> Processor_Options.Blender_OPT._LocalCIP (offset 24.0)
[00:51:18] Mapeando STAT0.STAT1.STAT34 -> Processor_Options.Blender_OPT._ICS_CustomerHotWater (offset 24.1)
[00:51:18] Mapeando STAT0.STAT1.STAT35 -> Processor_Options.Blender_OPT._ICS_CustomerChemRecov (offset 24.2)
[00:51:18] Mapeando STAT0.STAT1.STAT36 -> Processor_Options.Blender_OPT._CIPSignalExchange (offset 24.3)
[00:51:18] Mapeando STAT0.STAT1.STAT37 -> Processor_Options.Blender_OPT._ICS_CustomerChemicals (offset 24.4)
[00:51:18] Mapeando STAT0.STAT1.STAT38 -> Processor_Options.Blender_OPT._CarboPresent (offset 24.5)
[00:51:18] Mapeando STAT0.STAT1.STAT39 -> Processor_Options.Blender_OPT._InverterSyrupPumpPPP302 (offset 24.6)
[00:51:18] Mapeando STAT0.STAT1.STAT40 -> Processor_Options.Blender_OPT._InverterWaterPumpPPN301 (offset 24.7)
[00:51:18] Mapeando STAT0.STAT1.STAT41 -> Processor_Options.Blender_OPT._DoubleDeair (offset 25.0)
[00:51:18] Mapeando STAT0.STAT1.STAT42 -> Processor_Options.Blender_OPT._DeairPreMixed (offset 25.1)
[00:51:18] Mapeando STAT0.STAT1.STAT43 -> Processor_Options.Blender_OPT._Deaireation (offset 25.2)
[00:51:18] Mapeando STAT0.STAT1.STAT44 -> Processor_Options.Blender_OPT._StillWaterByPass (offset 25.3)
[00:51:18] Mapeando STAT0.STAT1.STAT45 -> Processor_Options.Blender_OPT._ManifoldSetting (offset 25.4)
[00:51:18] Mapeando STAT0.STAT1.STAT46 -> Processor_Options.Blender_OPT._InverterProdPumpPPM303 (offset 25.5)
[00:51:18] Mapeando STAT0.STAT1.STAT47 -> Processor_Options.Blender_OPT._SidelCip (offset 25.6)
[00:51:18] Mapeando STAT0.STAT1.STAT48 -> Processor_Options.Blender_OPT._EthernetCom_CpuPN_CP (offset 25.7)
[00:51:18] Mapeando STAT0.STAT1.STAT49 -> Processor_Options.Blender_OPT._2ndOutlet (offset 26.0)
[00:51:18] Mapeando STAT0.STAT1.STAT50 -> Processor_Options.Blender_OPT._Promass (offset 28.0)
[00:51:18] Mapeando STAT0.STAT1.STAT51 -> Processor_Options.Blender_OPT._WaterPromass (offset 30.0)
[00:51:18] Mapeando STAT0.STAT1.STAT52 -> Processor_Options.Blender_OPT._ProductConductimeter (offset 30.1)
[00:51:18] Mapeando STAT0.STAT1.STAT53 -> Processor_Options.Blender_OPT._ICS_CustomerH2ORecov (offset 30.2)
[00:51:18] Mapeando STAT0.STAT1.STAT54 -> Processor_Options.Blender_OPT.Spare303 (offset 30.3)
[00:51:18] Mapeando STAT0.STAT1.STAT55 -> Processor_Options.Blender_OPT._CO2_GAS2_Injection (offset 30.4)
[00:51:18] Mapeando STAT0.STAT1.STAT56 -> Processor_Options.Blender_OPT._InverterVacuuPumpPPN304 (offset 30.5)
[00:51:18] Mapeando STAT0.STAT1.STAT57 -> Processor_Options.Blender_OPT._InverterBoostPumpPPM307 (offset 30.6)
[00:51:18] Mapeando STAT0.STAT1.STAT58 -> Processor_Options.Blender_OPT._RunOut_Water (offset 30.7)
[00:51:18] Mapeando STAT0.STAT1.STAT59 -> Processor_Options.Blender_OPT._FlowMeterType (offset 31.0)
[00:51:18] Mapeando STAT0.STAT1.STAT60 -> Processor_Options.Blender_OPT._SidelFiller (offset 31.1)
[00:51:18] Mapeando STAT0.STAT1.STAT61 -> Processor_Options.Blender_OPT._Simulation (offset 31.2)
[00:51:18] Mapeando STAT0.STAT1.STAT62 -> Processor_Options.Blender_OPT._ProductCoolingCTRL (offset 31.3)
[00:51:18] Mapeando STAT0.STAT1.STAT63 -> Processor_Options.Blender_OPT._ChillerCTRL (offset 31.4)
[00:51:18] Mapeando STAT0.STAT1.STAT64 -> Processor_Options.Blender_OPT._CO2_SterileFilter (offset 31.5)
[00:51:18] Mapeando STAT0.STAT1.STAT65 -> Processor_Options.Blender_OPT._InverterRecirPumpPPM306 (offset 31.6)
[00:51:18] Mapeando STAT0.STAT1.STAT66 -> Processor_Options.Blender_OPT._ProdPressReleaseRVM304 (offset 31.7)
[00:51:18] Mapeando STAT0.STAT1.STAT67 -> Processor_Options.Blender_OPT._VacuumPump (offset 32.0)
[00:51:18] Mapeando STAT0.STAT1.STAT68 -> Processor_Options.Blender_OPT._GAS2InjectionType (offset 34.0)
[00:51:18] Mapeando STAT0.STAT1.STAT69 -> Processor_Options.Blender_OPT._InjectionPress_Ctrl (offset 36.0)
[00:51:18] Mapeando STAT0.STAT1.STAT70 -> Processor_Options.Blender_OPT._ProdPressureType (offset 38.0)
[00:51:18] Mapeando STAT0.STAT1.STAT71 -> Processor_Options.Blender_OPT._CIPHeatType (offset 40.0)
[00:51:18] Mapeando STAT0.STAT1.STAT72 -> Processor_Options.Blender_OPT._EHS_NrRes (offset 42.0)
[00:51:18] Mapeando STAT73[1] -> Spare1 (offset 44.0)
[00:51:18] Mapeando STAT73[2] -> Spare1 (offset 44.0)
[00:51:18] Mapeando STAT73[3] -> Spare1 (offset 44.0)
[00:51:18] Mapeando STAT73[4] -> Spare1 (offset 44.0)
[00:51:18] Mapeando STAT73[5] -> Spare1 (offset 44.0)
[00:51:18] Mapeando STAT73[6] -> Spare1 (offset 44.0)
[00:51:18] Mapeando STAT73[7] -> Spare1 (offset 44.0)
[00:51:18] Mapeando STAT73[8] -> Spare1 (offset 44.0)
[00:51:18] Mapeando STAT73[9] -> Spare1 (offset 44.0)
[00:51:18] Mapeando STAT74 -> _RVM301_DeadBand (offset 62.0)
[00:51:18] Mapeando STAT75 -> _RVM301_Kp (offset 66.0)
[00:51:18] Mapeando STAT76.STAT77 -> Actual_Recipe_Parameters._Name (offset 70.0)
[00:51:18] Mapeando STAT76.STAT78 -> Actual_Recipe_Parameters._EnProdTemp (offset 104.0)
[00:51:18] Mapeando STAT76.STAT79 -> Actual_Recipe_Parameters._SyrFlushing (offset 104.1)
[00:51:18] Mapeando STAT76.STAT80 -> Actual_Recipe_Parameters._GAS2_Injection (offset 104.2)
[00:51:18] Mapeando STAT76.STAT81 -> Actual_Recipe_Parameters._Eq_Pression_Selected (offset 104.3)
[00:51:18] Mapeando STAT76.STAT82 -> Actual_Recipe_Parameters._DeoxStripEn (offset 104.4)
[00:51:18] Mapeando STAT76.STAT83 -> Actual_Recipe_Parameters._DeoxVacuumEn (offset 104.5)
[00:51:18] Mapeando STAT76.STAT84 -> Actual_Recipe_Parameters._DeoxPreMixed (offset 104.6)
[00:51:18] Mapeando STAT76.STAT85 -> Actual_Recipe_Parameters._EnBlowOffProdPipeCO2Fil (offset 104.7)
[00:51:18] Mapeando STAT76.STAT86 -> Actual_Recipe_Parameters._WaterSelection (offset 105.0)
[00:51:18] Mapeando STAT76.STAT87 -> Actual_Recipe_Parameters._FillerNextRecipeNum (offset 106.0)
[00:51:18] Mapeando STAT76.STAT88 -> Actual_Recipe_Parameters._BottleShape (offset 107.0)
[00:51:18] Mapeando STAT76.STAT89 -> Actual_Recipe_Parameters._Type (offset 108.0)
[00:51:18] Mapeando STAT76.STAT90 -> Actual_Recipe_Parameters._ProdMeterRecipeNum (offset 110.0)
[00:51:18] Mapeando STAT76.STAT91 -> Actual_Recipe_Parameters._SyrupBrix (offset 112.0)
[00:51:18] Mapeando STAT76.STAT92 -> Actual_Recipe_Parameters._SyrupDensity (offset 116.0)
[00:51:18] Mapeando STAT76.STAT93 -> Actual_Recipe_Parameters._SyrupFactor (offset 120.0)
[00:51:18] Mapeando STAT76.STAT94 -> Actual_Recipe_Parameters._ProductBrix (offset 124.0)
[00:51:18] Mapeando STAT76.STAT95 -> Actual_Recipe_Parameters._ProductionRate (offset 128.0)
[00:51:18] Mapeando STAT76.STAT96 -> Actual_Recipe_Parameters._Ratio (offset 132.0)
[00:51:18] Mapeando STAT76.STAT97 -> Actual_Recipe_Parameters._ProdBrixOffset (offset 136.0)
[00:51:18] Mapeando STAT76.STAT98 -> Actual_Recipe_Parameters._CO2Vols (offset 140.0)
[00:51:18] Mapeando STAT76.STAT99 -> Actual_Recipe_Parameters._CO2Fact (offset 144.0)
[00:51:18] Mapeando STAT76.STAT100 -> Actual_Recipe_Parameters._ProdTankPress (offset 148.0)
[00:51:18] Mapeando STAT76.STAT101 -> Actual_Recipe_Parameters._SP_ProdTemp (offset 152.0)
[00:51:18] Mapeando STAT76.STAT102 -> Actual_Recipe_Parameters._PrdTankMinLevel (offset 156.0)
[00:51:18] Mapeando STAT76.STAT103 -> Actual_Recipe_Parameters._WaterValveSave (offset 160.0)
[00:51:18] Mapeando STAT76.STAT104 -> Actual_Recipe_Parameters._SyrupValveSave (offset 164.0)
[00:51:18] Mapeando STAT76.STAT105 -> Actual_Recipe_Parameters._CarboCO2ValveSave (offset 168.0)
[00:51:18] Mapeando STAT76.STAT106 -> Actual_Recipe_Parameters._ProdMeterHighBrix (offset 172.0)
[00:51:18] Mapeando STAT76.STAT107 -> Actual_Recipe_Parameters._ProdMeterLowBrix (offset 176.0)
[00:51:18] Mapeando STAT76.STAT108 -> Actual_Recipe_Parameters._ProdMeterHighCO2 (offset 180.0)
[00:51:18] Mapeando STAT76.STAT109 -> Actual_Recipe_Parameters._ProdMeterLowCO2 (offset 184.0)
[00:51:18] Mapeando STAT76.STAT110 -> Actual_Recipe_Parameters._ProdMeter_ZeroCO2 (offset 188.0)
[00:51:18] Mapeando STAT76.STAT111 -> Actual_Recipe_Parameters._ProdMeter_ZeroBrix (offset 192.0)
[00:51:18] Mapeando STAT76.STAT112 -> Actual_Recipe_Parameters._ProdHighCond (offset 196.0)
[00:51:18] Mapeando STAT76.STAT113 -> Actual_Recipe_Parameters._ProdLowCond (offset 200.0)
[00:51:18] Mapeando STAT76.STAT114 -> Actual_Recipe_Parameters._BottleSize (offset 204.0)
[00:51:18] Mapeando STAT76.STAT115 -> Actual_Recipe_Parameters._FillingValveHead_SP (offset 208.0)
[00:51:18] Mapeando STAT76.STAT116 -> Actual_Recipe_Parameters._SyrMeter_ZeroBrix (offset 212.0)
[00:51:18] Mapeando STAT76.STAT117 -> Actual_Recipe_Parameters._FirstProdExtraCO2Fact (offset 216.0)
[00:51:18] Mapeando STAT76.STAT118 -> Actual_Recipe_Parameters._Gas2Vols (offset 220.0)
[00:51:18] Mapeando STAT76.STAT119 -> Actual_Recipe_Parameters._Gas2Fact (offset 224.0)
[00:51:18] Mapeando STAT76.STAT120 -> Actual_Recipe_Parameters._SyrupPumpPressure (offset 228.0)
[00:51:18] Mapeando STAT76.STAT121 -> Actual_Recipe_Parameters._WaterPumpPressure (offset 232.0)
[00:51:18] Mapeando STAT76.STAT122 -> Actual_Recipe_Parameters._CO2_Air_N2_PressSelect (offset 236.0)
[00:51:18] Mapeando STAT76.STAT123 -> Actual_Recipe_Parameters._KFactRVM304BlowOff (offset 238.0)
[00:51:18] Mapeando STAT76.STAT124 -> Actual_Recipe_Parameters._ProdRecircPumpFreq (offset 242.0)
[00:51:18] Mapeando STAT76.STAT125 -> Actual_Recipe_Parameters._ProdBoosterPumpPress (offset 246.0)
[00:51:18] Mapeando STAT76.STAT126 -> Actual_Recipe_Parameters._ProdSendPumpFreq (offset 250.0)
[00:51:18] Mapeando STAT127[1] -> Spare2 (offset 254.0)
[00:51:18] Mapeando STAT127[2] -> Spare2 (offset 254.0)
[00:51:18] Mapeando STAT127[3] -> Spare2 (offset 254.0)
[00:51:18] Mapeando STAT127[4] -> Spare2 (offset 254.0)
[00:51:18] Mapeando STAT127[5] -> Spare2 (offset 254.0)
[00:51:18] Mapeando STAT128 -> Next_Recipe_Name (offset 264.0)
[00:51:18] Mapeando STAT129 -> Next_Recipe_Number (offset 298.0)
[00:51:18] Mapeando STAT130[1] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[2] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[3] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[4] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[5] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[6] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[7] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[8] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[9] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[10] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[11] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[12] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[13] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[14] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[15] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[16] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[17] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT130[18] -> Spare3 (offset 300.0)
[00:51:18] Mapeando STAT131.STAT132 -> ProcessSetup.Spare000 (offset 336.0)
[00:51:18] Mapeando STAT131.STAT133 -> ProcessSetup.Spare040 (offset 340.0)
[00:51:18] Mapeando STAT131.STAT134 -> ProcessSetup._KWaterLoss (offset 344.0)
[00:51:18] Mapeando STAT131.STAT135 -> ProcessSetup._KSyrupLoss (offset 348.0)
[00:51:18] Mapeando STAT131.STAT136 -> ProcessSetup._KProdLoss (offset 352.0)
[00:51:18] Mapeando STAT131.STAT137 -> ProcessSetup._KPPM303 (offset 356.0)
[00:51:18] Mapeando STAT131.STAT138 -> ProcessSetup._BaialageRVM301OVMin (offset 360.0)
[00:51:18] Mapeando STAT131.STAT139 -> ProcessSetup._SyrupLinePressure (offset 364.0)
[00:51:18] Mapeando STAT131.STAT140 -> ProcessSetup._CIPRMM301OV (offset 368.0)
[00:51:18] Mapeando STAT131.STAT141 -> ProcessSetup._CIPRMP302OV (offset 372.0)
[00:51:18] Mapeando STAT131.STAT142 -> ProcessSetup._CIPTM301MinLevel (offset 376.0)
[00:51:18] Mapeando STAT131.STAT143 -> ProcessSetup._CIPTM301MaxLevel (offset 380.0)
[00:51:18] Mapeando STAT131.STAT144 -> ProcessSetup._CIPPPM303Freq (offset 384.0)
[00:51:18] Mapeando STAT131.STAT145 -> ProcessSetup._CIPTP301MinLevel (offset 388.0)
[00:51:18] Mapeando STAT131.STAT146 -> ProcessSetup._CIPTP301MaxLevel (offset 392.0)
[00:51:18] Mapeando STAT131.STAT147 -> ProcessSetup._RinseRMM301OV (offset 396.0)
[00:51:18] Mapeando STAT131.STAT148 -> ProcessSetup._RinseRMP302OV (offset 400.0)
[00:51:18] Mapeando STAT131.STAT149 -> ProcessSetup._RinseTM301Press (offset 404.0)
[00:51:18] Mapeando STAT131.STAT150 -> ProcessSetup._RinsePPM303Freq (offset 408.0)
[00:51:18] Mapeando STAT131.STAT151 -> ProcessSetup._DrainTM301Press (offset 412.0)
[00:51:18] Mapeando STAT131.STAT152 -> ProcessSetup._KRecBlendError (offset 416.0)
[00:51:18] Mapeando STAT131.STAT153 -> ProcessSetup._KRecCarboCO2Error (offset 420.0)
[00:51:18] Mapeando STAT131.STAT154 -> ProcessSetup._MaxBlendError (offset 424.0)
[00:51:18] Mapeando STAT131.STAT155 -> ProcessSetup._MaxCarboCO2Error (offset 428.0)
[00:51:18] Mapeando STAT131.STAT156 -> ProcessSetup._StartUpBrixExtraWater (offset 432.0)
[00:51:18] Mapeando STAT131.STAT157 -> ProcessSetup._StartUpCO2ExtraWater (offset 436.0)
[00:51:18] Mapeando STAT131.STAT158 -> ProcessSetup._StartUpPPM303Freq (offset 440.0)
[00:51:18] Mapeando STAT131.STAT159 -> ProcessSetup._SyrupRoomTank (offset 444.0)
[00:51:18] Mapeando STAT131.STAT160 -> ProcessSetup._SyrupRunOutLiters (offset 446.0)
[00:51:18] Mapeando STAT131.STAT161 -> ProcessSetup._InjCO2Press_Offset (offset 450.0)
[00:51:18] Mapeando STAT131.STAT162 -> ProcessSetup._InjCO2Press_MinFlow (offset 454.0)
[00:51:18] Mapeando STAT131.STAT163 -> ProcessSetup._InjCO2Press_MaxFlow (offset 458.0)
[00:51:18] Mapeando STAT131.STAT164 -> ProcessSetup._CarboCO2Pressure (offset 462.0)
[00:51:18] Mapeando STAT131.STAT165 -> ProcessSetup._N2MinPressure (offset 466.0)
[00:51:18] Mapeando STAT131.STAT166 -> ProcessSetup._DiffSensor_Height (offset 470.0)
[00:51:18] Mapeando STAT131.STAT167 -> ProcessSetup._DiffSensor_DeltaHeight (offset 474.0)
[00:51:18] Mapeando STAT131.STAT168 -> ProcessSetup._DiffSensor_Offset (offset 478.0)
[00:51:18] Mapeando STAT131.STAT169 -> ProcessSetup._FillingValveHeight (offset 482.0)
[00:51:18] Mapeando STAT131.STAT170 -> ProcessSetup._FillerDiameter (offset 486.0)
[00:51:18] Mapeando STAT131.STAT171 -> ProcessSetup._FillingValveNum (offset 490.0)
[00:51:18] Mapeando STAT131.STAT172 -> ProcessSetup._FillerProdPipeDN (offset 492.0)
[00:51:18] Mapeando STAT131.STAT173 -> ProcessSetup._FillerProdPipeMass (offset 496.0)
[00:51:18] Mapeando STAT131.STAT174 -> ProcessSetup._FillingTime (offset 500.0)
[00:51:18] Mapeando STAT131.STAT175 -> ProcessSetup._TM301Height_0 (offset 504.0)
[00:51:18] Mapeando STAT131.STAT176 -> ProcessSetup._TM301LevelPerc_2 (offset 508.0)
[00:51:18] Mapeando STAT131.STAT177 -> ProcessSetup._TM301Height_2 (offset 512.0)
[00:51:18] Mapeando STAT131.STAT178 -> ProcessSetup._RVN304Factor (offset 516.0)
[00:51:18] Mapeando STAT131.STAT179 -> ProcessSetup._DrainTM301Flushing (offset 520.0)
[00:51:18] Mapeando STAT131.STAT180 -> ProcessSetup._FirstProdExtraBrix (offset 524.0)
[00:51:18] Mapeando STAT131.STAT181 -> ProcessSetup._FirstProdDietExtraSyr (offset 528.0)
[00:51:18] Mapeando STAT131.STAT182 -> ProcessSetup._EndProdLastSyrlt (offset 532.0)
[00:51:18] Mapeando STAT131.STAT183 -> ProcessSetup._TM301DrainSt0Time (offset 536.0)
[00:51:18] Mapeando STAT131.STAT184 -> ProcessSetup._TM301DrainSt1Time (offset 538.0)
[00:51:18] Mapeando STAT131.STAT185 -> ProcessSetup._ProdPipeRunOutSt0Time (offset 540.0)
[00:51:18] Mapeando STAT131.STAT186 -> ProcessSetup._RMM301ProdPipeRunOu (offset 542.0)
[00:51:18] Mapeando STAT131.STAT187 -> ProcessSetup._RMP302ProdPipeRunOu (offset 546.0)
[00:51:18] Mapeando STAT131.STAT188 -> ProcessSetup._ProdPipeRunOutAmount (offset 550.0)
[00:51:18] Mapeando STAT131.STAT189 -> ProcessSetup._TM301RunOutChiller (offset 554.0)
[00:51:18] Mapeando STAT131.STAT190 -> ProcessSetup._MinSpeedNominalProd (offset 558.0)
[00:51:18] Mapeando STAT131.STAT191 -> ProcessSetup._MinSpeedSlowProd (offset 562.0)
[00:51:18] Mapeando STAT131.STAT192 -> ProcessSetup._FastChgOvrTM301DrnPrss (offset 566.0)
[00:51:18] Mapeando STAT131.STAT193 -> ProcessSetup._CIPTN301MinLevel (offset 570.0)
[00:51:18] Mapeando STAT131.STAT194 -> ProcessSetup._CIPTN301MaxLevel (offset 574.0)
[00:51:18] Mapeando STAT131.STAT195 -> ProcessSetup._ProdPPN304Freq (offset 578.0)
[00:51:18] Mapeando STAT131.STAT196 -> ProcessSetup._GAS2InjectionPress (offset 582.0)
[00:51:18] Mapeando STAT131.STAT197 -> ProcessSetup._BaialageRVM301OVMax (offset 586.0)
[00:51:18] Mapeando STAT131.STAT198 -> ProcessSetup._RinsePPN301Freq (offset 590.0)
[00:51:18] Mapeando STAT131.STAT199 -> ProcessSetup._CIPPPN301Freq (offset 594.0)
[00:51:18] Mapeando STAT131.STAT200 -> ProcessSetup._RinsePPP302Freq (offset 598.0)
[00:51:18] Mapeando STAT131.STAT201 -> ProcessSetup._CIPPPP302Freq (offset 602.0)
[00:51:18] Mapeando STAT131.STAT202 -> ProcessSetup._PercSyrupBrixSyrStarUp (offset 606.0)
[00:51:18] Mapeando STAT131.STAT203 -> ProcessSetup._RefTempCoolingCTRL (offset 610.0)
[00:51:18] Mapeando STAT131.STAT204 -> ProcessSetup._H2OSerpPrimingVolume (offset 614.0)
[00:51:18] Mapeando STAT131.STAT205 -> ProcessSetup._AVN301_Nozzle_Kv (offset 618.0)
[00:51:18] Mapeando STAT131.STAT206 -> ProcessSetup._AVN302_Nozzle_Kv (offset 622.0)
[00:51:18] Mapeando STAT131.STAT207 -> ProcessSetup._AVN303_Nozzle_Kv (offset 626.0)
[00:51:18] Mapeando STAT131.STAT208 -> ProcessSetup._DeoxSpryball_Kv (offset 630.0)
[00:51:18] Mapeando STAT131.STAT209 -> ProcessSetup._PremixedLineDrainTime (offset 634.0)
[00:51:18] Mapeando STAT131.STAT210 -> ProcessSetup._PPN301_H_MaxFlow (offset 636.0)
[00:51:18] Mapeando STAT131.STAT211 -> ProcessSetup._PPN301_H_MinFlow (offset 640.0)
[00:51:18] Mapeando STAT131.STAT212 -> ProcessSetup._PPN301_MaxFlow (offset 644.0)
[00:51:18] Mapeando STAT131.STAT213 -> ProcessSetup._PPN301_MinFlow (offset 648.0)
[00:51:18] Mapeando STAT131.STAT214 -> ProcessSetup._PPP302_H_MaxFlow (offset 652.0)
[00:51:18] Mapeando STAT131.STAT215 -> ProcessSetup._PPP302_H_MinFlow (offset 656.0)
[00:51:18] Mapeando STAT131.STAT216 -> ProcessSetup._PPP302_MaxFlow (offset 660.0)
[00:51:18] Mapeando STAT131.STAT217 -> ProcessSetup._PPP302_MinFlow (offset 664.0)
[00:51:18] Mapeando STAT131.STAT218 -> ProcessSetup._RinsePPM306Freq (offset 668.0)
[00:51:18] Mapeando STAT131.STAT219 -> ProcessSetup._CIPPPM306Freq (offset 672.0)
[00:51:18] Mapeando STAT131.STAT220 -> ProcessSetup._PPM307_H_MaxFlow (offset 676.0)
[00:51:18] Mapeando STAT131.STAT221 -> ProcessSetup._PPM307_H_MinFlow (offset 680.0)
[00:51:18] Mapeando STAT131.STAT222 -> ProcessSetup._PPM307_MaxFlow (offset 684.0)
[00:51:18] Mapeando STAT131.STAT223 -> ProcessSetup._PPM307_MinFlow (offset 688.0)
[00:51:18] Mapeando STAT131.STAT224 -> ProcessSetup._Temp0_VacuumCtrl (offset 692.0)
[00:51:18] Mapeando STAT131.STAT225 -> ProcessSetup._Temp1_VacuumCtrl (offset 696.0)
[00:51:18] Mapeando STAT131.STAT226 -> ProcessSetup._Temp2_VacuumCtrl (offset 700.0)
[00:51:18] Mapeando STAT131.STAT227 -> ProcessSetup._Temp3_VacuumCtrl (offset 704.0)
[00:51:18] Mapeando STAT131.STAT228 -> ProcessSetup._Temp4_VacuumCtrl (offset 708.0)
[00:51:18] Mapeando STAT131.STAT229 -> ProcessSetup._T1_VacuumCtrl (offset 712.0)
[00:51:18] Mapeando STAT131.STAT230 -> ProcessSetup._T2_VacuumCtrl (offset 716.0)
[00:51:18] Mapeando STAT131.STAT231 -> ProcessSetup._T3_VacuumCtrl (offset 720.0)
[00:51:18] Mapeando STAT131.STAT232 -> ProcessSetup._T4_VacuumCtrl (offset 724.0)
[00:51:18] Mapeando STAT131.STAT233 -> ProcessSetup._ICS_VolDosWorkTimePAA (offset 728.0)
[00:51:18] Mapeando STAT131.STAT234 -> ProcessSetup._ICS_VolPauseTimePAA (offset 730.0)
[00:51:18] Mapeando STAT131.STAT235 -> ProcessSetup._ICS_PAAPulseWeight (offset 732.0)
[00:51:18] Mapeando STAT131.STAT236 -> ProcessSetup._ICS_CausticPulseWeight (offset 734.0)
[00:51:18] Mapeando STAT131.STAT237 -> ProcessSetup._ICS_AcidPulseWeight (offset 736.0)
[00:51:18] Mapeando STAT131.STAT238 -> ProcessSetup._ICS_VolumeRestOfLine (offset 738.0)
[00:51:18] Mapeando STAT131.STAT239 -> ProcessSetup._ICS_VolDosWorkTimeCaus (offset 742.0)
[00:51:18] Mapeando STAT131.STAT240 -> ProcessSetup._ICS_VolDosPauseTimeCaus (offset 744.0)
[00:51:18] Mapeando STAT131.STAT241 -> ProcessSetup._ICS_VolDosWorkTimeAcid (offset 746.0)
[00:51:18] Mapeando STAT131.STAT242 -> ProcessSetup._ICS_VolDosPauseTimeAcid (offset 748.0)
[00:51:18] Mapeando STAT131.STAT243 -> ProcessSetup._ICS_ConcDosWorkTimeCaus (offset 750.0)
[00:51:18] Mapeando STAT131.STAT244 -> ProcessSetup._ICS_ConcDosPausTimeCaus (offset 752.0)
[00:51:18] Mapeando STAT131.STAT245 -> ProcessSetup._ICS_ConcDosWorkTimeAcid (offset 754.0)
[00:51:18] Mapeando STAT131.STAT246 -> ProcessSetup._ICS_ConcDosPausTimeAcid (offset 756.0)
[00:51:18] Mapeando STAT131.STAT247 -> ProcessSetup._RinsePPM307Freq (offset 758.0)
[00:51:18] Mapeando STAT131.STAT248 -> ProcessSetup._CIPPPM307Freq (offset 762.0)
[00:51:18] Mapeando STAT131.STAT249 -> ProcessSetup._CIP2StepTN301Lvl (offset 766.0)
[00:51:18] Mapeando STAT131.STAT250 -> ProcessSetup._CIP2StepTM301Lvl (offset 770.0)
[00:51:18] Mapeando STAT131.STAT251 -> ProcessSetup._CIP2StepTP301Lvl (offset 774.0)
[00:51:18] Mapeando STAT131.STAT252 -> ProcessSetup._PumpNominalFreq (offset 778.0)
[00:51:18] Mapeando STAT253 -> _SwitchOff_DensityOK (offset 782.0)
[00:51:18] Mapeando STAT254 -> STAT254 (offset 784.0)
[00:51:18] Archivo _updated generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\json\db1001_updated.json
[00:51:18] --- Proceso completado ---
[00:51:18] Ejecución de x7_value_updater.py finalizada (success). Duración: 0:00:00.223903.
[00:51:18] Log completo guardado en: D:\Proyectos\Scripts\ParamManagerScripts\backend\script_groups\S7_DB_Utils\log_x7_value_updater.txt
[00:51:35] Iniciando ejecución de x4.py en C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001...
[00:51:35] Using working directory: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001
[00:51:35] Los archivos de documentación generados se guardarán en: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation
[00:51:35] Archivos JSON encontrados para procesar: 3
[00:51:35] --- Procesando archivo JSON: db1001_data.json ---
[00:51:35] Archivo JSON 'db1001_data.json' cargado correctamente.
[00:51:35] INFO: Usando '_begin_block_assignments_ordered' para generar bloque BEGIN de DB 'HMI_Blender_Parameters'.
[00:51:35] Archivo S7 reconstruido generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_data.txt
[00:51:35] Archivo Markdown de documentación generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_data.md
[00:51:35] --- Procesando archivo JSON: db1001_format.json ---
[00:51:35] Archivo JSON 'db1001_format.json' cargado correctamente.
[00:51:35] INFO: Usando '_begin_block_assignments_ordered' para generar bloque BEGIN de DB 'HMI_Blender_Parameters'.
[00:51:35] Archivo S7 reconstruido generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_format.txt
[00:51:35] Archivo Markdown de documentación generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_format.md
[00:51:35] --- Procesando archivo JSON: db1001_updated.json ---
[00:51:35] Archivo JSON 'db1001_updated.json' cargado correctamente.
[00:51:35] INFO: Usando '_begin_block_assignments_ordered' para generar bloque BEGIN de DB 'HMI_Blender_Parameters'.
[00:51:35] Archivo S7 reconstruido generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_updated.txt
[00:51:35] Archivo Markdown de documentación generado: C:\Trabajo\SIDEL\09 - SAE452 - Diet as Regular - San Giovanni in Bosco\Reporte\DB1001\documentation\db1001_updated.md
[00:51:35] --- Proceso de generación de documentación completado ---
[00:51:35] Ejecución de x4.py finalizada (success). Duración: 0:00:00.110751.
[00:51:35] Log completo guardado en: D:\Proyectos\Scripts\ParamManagerScripts\backend\script_groups\S7_DB_Utils\log_x4.txt