From 4eed5d268793641f3623fa94b703d11d7d734cc9 Mon Sep 17 00:00:00 2001 From: Miguel Date: Thu, 28 Aug 2025 13:31:11 +0200 Subject: [PATCH] feat: Add CPU status retrieval and display in dashboard - Implemented `get_cpu_status` method in PLCClient to fetch current CPU state, cycle time, and additional CPU info. - Created a new API endpoint `/api/plc/status` to serve CPU status data. - Updated frontend to load and display CPU status in the Dashboard, including state and cycle time. - Added error handling for CPU status retrieval in the frontend. --- application_events.json | 2364 ++++++++++++++---------------- core/plc_client.py | 61 + frontend/src/pages/Dashboard.jsx | 54 + frontend/src/services/api.js | 8 + main.py | 14 + system_state.json | 2 +- 6 files changed, 1236 insertions(+), 1267 deletions(-) diff --git a/application_events.json b/application_events.json index 1b3a8bf..8e7bfc6 100644 --- a/application_events.json +++ b/application_events.json @@ -1,1270 +1,5 @@ { "events": [ - { - "timestamp": "2025-08-27T14:14:10.289240", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.016944169998169, - "points_saved": 20, - "points_rate": 1.9966168983852544, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.025434625148773194, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:14:20.306186", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.016994953155518, - "points_saved": 20, - "points_rate": 1.9966067761369564, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.032395803928375246, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:14:30.322665", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.017037391662598, - "points_saved": 20, - "points_rate": 1.996598317247617, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.024763011932373048, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:14:40.340151", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.016884565353394, - "points_saved": 20, - "points_rate": 1.9966287790893, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.025506973266601562, - "csv_write_time_avg": 3.3855438232421873e-06 - } - }, - { - "timestamp": "2025-08-27T14:14:50.357402", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.017219543457031, - "points_saved": 20, - "points_rate": 1.996562011368059, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.025593316555023192, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:15:00.375478", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.018708944320679, - "points_saved": 20, - "points_rate": 1.9962651985550923, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.026975929737091064, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:15:10.399729", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.023703336715698, - "points_saved": 20, - "points_rate": 1.995270543047922, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02684429883956909, - "csv_write_time_avg": 2.956390380859375e-06 - } - }, - { - "timestamp": "2025-08-27T14:15:20.416482", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.017300367355347, - "points_saved": 20, - "points_rate": 1.996545902244935, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02789478302001953, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:15:30.434442", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.01737666130066, - "points_saved": 20, - "points_rate": 1.9965306962315215, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.024824726581573486, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:15:40.452111", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.018253326416016, - "points_saved": 20, - "points_rate": 1.9963559862540339, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.025231122970581055, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:15:50.471205", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.01856780052185, - "points_saved": 20, - "points_rate": 1.9962933223806933, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.023374950885772704, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:16:00.489822", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.019142389297485, - "points_saved": 20, - "points_rate": 1.996178836759934, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.03157364130020142, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:16:10.507301", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.017479181289673, - "points_saved": 20, - "points_rate": 1.9965102635157317, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.027073073387145995, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:16:20.527121", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", - "details": { - "duration": 10.019195556640625, - "points_saved": 20, - "points_rate": 1.9961682439409214, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.3, - "cpu_max": 0.3, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.027773118019104003, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:16:30.546622", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.0201256275177, - "points_saved": 20, - "points_rate": 1.9959829590434615, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02579970359802246, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:16:40.567381", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.020759582519531, - "points_saved": 20, - "points_rate": 1.9958566848453794, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.024775385856628418, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:16:50.588489", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", - "details": { - "duration": 10.021107196807861, - "points_saved": 20, - "points_rate": 1.9957874521460892, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.3, - "cpu_max": 0.3, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.028467869758605956, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:17:00.611615", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.023125886917114, - "points_saved": 20, - "points_rate": 1.995385494070807, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.026097214221954344, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:17:10.628474", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", - "details": { - "duration": 10.016859531402588, - "points_saved": 20, - "points_rate": 1.9966337690271618, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.3, - "cpu_max": 0.3, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.025484120845794676, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:17:20.657365", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.02889084815979, - "points_saved": 20, - "points_rate": 1.9942384758998366, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02662050724029541, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:17:30.675395", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", - "details": { - "duration": 10.018029928207397, - "points_saved": 20, - "points_rate": 1.9964005042235637, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.3, - "cpu_max": 0.3, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.026105713844299317, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:17:40.694035", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.018086910247803, - "points_saved": 20, - "points_rate": 1.99638914886448, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.028483247756958006, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:17:50.711733", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.017741203308105, - "points_saved": 20, - "points_rate": 1.9964580431959558, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.027032029628753663, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:18:00.730334", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.019110441207886, - "points_saved": 20, - "points_rate": 1.9961852020057018, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02799462080001831, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:18:10.751089", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.019737005233765, - "points_saved": 20, - "points_rate": 1.996060374593973, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02386442422866821, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:18:20.772174", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.022103071212769, - "points_saved": 20, - "points_rate": 1.9955891351234938, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.027265465259552, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:18:30.790586", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.017896175384521, - "points_saved": 20, - "points_rate": 1.996427158942115, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02558964490890503, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:18:40.817891", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.02782130241394, - "points_saved": 20, - "points_rate": 1.9944511770653026, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.027964210510253905, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:18:50.836601", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.018709897994995, - "points_saved": 20, - "points_rate": 1.996265008531939, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.028523671627044677, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:19:00.857753", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.021151542663574, - "points_saved": 20, - "points_rate": 1.9957786203364904, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02696237564086914, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:19:10.877703", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.019950866699219, - "points_saved": 20, - "points_rate": 1.9960177715510514, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02571762800216675, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:19:20.895968", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", - "details": { - "duration": 10.018264770507812, - "points_saved": 20, - "points_rate": 1.9963537057711669, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.3, - "cpu_max": 0.3, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.025138342380523683, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:19:30.922337", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.026368379592896, - "points_saved": 20, - "points_rate": 1.9947401933392823, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02520761489868164, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:19:40.941481", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.018107652664185, - "points_saved": 20, - "points_rate": 1.9963850153557954, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02617049217224121, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:19:50.960475", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.020030975341797, - "points_saved": 20, - "points_rate": 1.9960018136887818, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02888997793197632, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:20:00.979541", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 21 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.019065856933594, - "points_saved": 21, - "points_rate": 2.096003789162356, - "variables_saved": 84, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.025046609696887788, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:20:10.999294", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.019753217697144, - "points_saved": 20, - "points_rate": 1.9960571448681481, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.023628616333007814, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:20:21.019870", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", - "details": { - "duration": 10.02006483078003, - "points_saved": 20, - "points_rate": 1.995995069668932, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.3, - "cpu_max": 0.3, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.026502788066864014, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:20:31.038745", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.019385814666748, - "points_saved": 20, - "points_rate": 1.9961303387202896, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.025163328647613524, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:20:41.056385", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.017640352249146, - "points_saved": 20, - "points_rate": 1.996478142231332, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.025907087326049804, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:20:51.074428", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.01804256439209, - "points_saved": 20, - "points_rate": 1.9963979860783942, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.029744672775268554, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:21:01.095488", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.0210599899292, - "points_saved": 20, - "points_rate": 1.9957968538357491, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02635519504547119, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:21:11.126218", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.030183553695679, - "points_saved": 20, - "points_rate": 1.9939814553673731, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.025286662578582763, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:21:21.145664", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.01999282836914, - "points_saved": 20, - "points_rate": 1.996009412638992, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02801856994628906, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:21:31.165070", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.01889967918396, - "points_saved": 20, - "points_rate": 1.9962271946442927, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02562590837478638, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:21:41.184650", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.020086526870728, - "points_saved": 20, - "points_rate": 1.995990747821017, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.028649497032165527, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:21:51.202589", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.017938137054443, - "points_saved": 20, - "points_rate": 1.9964187966008506, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02413393259048462, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:22:01.222612", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.01944899559021, - "points_saved": 20, - "points_rate": 1.996117751465421, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.024640440940856934, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:22:11.240052", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.018014907836914, - "points_saved": 20, - "points_rate": 1.9964034974987268, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.0244159460067749, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:22:21.258636", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", - "details": { - "duration": 10.018583059310913, - "points_saved": 20, - "points_rate": 1.9962902819289117, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.3, - "cpu_max": 0.3, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.02707031965255737, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:22:31.277833", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.018651723861694, - "points_saved": 20, - "points_rate": 1.996276600010504, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.026224517822265626, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:22:41.295975", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", - "details": { - "duration": 10.01868724822998, - "points_saved": 20, - "points_rate": 1.9962695215916073, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.0, - "cpu_max": 0.0, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.03213200569152832, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:22:51.321939", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.025457859039307, - "points_saved": 20, - "points_rate": 1.9949213573290614, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.024122965335845948, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:23:01.345696", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", - "details": { - "duration": 10.024263381958008, - "points_saved": 20, - "points_rate": 1.9951590693433539, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.2, - "cpu_max": 0.2, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.024874019622802734, - "csv_write_time_avg": 0.0 - } - }, - { - "timestamp": "2025-08-27T14:23:11.375049", - "level": "info", - "event_type": "performance_report", - "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", - "details": { - "duration": 10.02935266494751, - "points_saved": 20, - "points_rate": 1.9941466481580417, - "variables_saved": 80, - "udp_points_sent": 0, - "points_lost": 0, - "cpu_average": 0.3, - "cpu_max": 0.3, - "delay_average": 0.0, - "delay_max": 0.0, - "read_errors": 0, - "csv_errors": 0, - "udp_errors": 0, - "read_time_avg": 0.030313146114349366, - "csv_write_time_avg": 0.0 - } - }, { "timestamp": "2025-08-27T14:23:21.395834", "level": "info", @@ -21990,8 +20725,1105 @@ "read_time_avg": 0.025986552238464355, "csv_write_time_avg": 0.0 } + }, + { + "timestamp": "2025-08-28T11:47:38.807163", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.6% CPU", + "details": { + "duration": 10.035170793533325, + "points_saved": 20, + "points_rate": 1.9929904942811758, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.6, + "cpu_max": 0.6, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.026740550994873047, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T11:47:48.852976", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.5% CPU", + "details": { + "duration": 10.045812845230103, + "points_saved": 20, + "points_rate": 1.9908792158611923, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.5, + "cpu_max": 0.5, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.02560896873474121, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T11:47:58.885093", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", + "details": { + "duration": 10.032117128372192, + "points_saved": 20, + "points_rate": 1.9935971384781064, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.0, + "cpu_max": 0.0, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.028562819957733153, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T11:47:58.916299", + "level": "info", + "event_type": "plot_session_created", + "message": "Plot session 'DAR_Brix' created and started", + "details": { + "session_id": "DAR_1756374478915_5", + "variables": [ + "HMI_Instrument.QTM306.PVFiltered", + "HMI_Instrument.QTM307.PVFiltered", + "AUX Blink_2.0S" + ], + "time_window": 60, + "trigger_variable": null, + "auto_started": true + } + }, + { + "timestamp": "2025-08-28T11:48:08.919507", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", + "details": { + "duration": 10.034414291381836, + "points_saved": 20, + "points_rate": 1.9931407473555496, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.0, + "cpu_max": 0.0, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.022832179069519044, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T11:48:18.966611", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", + "details": { + "duration": 10.04710340499878, + "points_saved": 20, + "points_rate": 1.9906234855758838, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.2, + "cpu_max": 0.2, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.028270864486694337, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T12:59:39.028950", + "level": "info", + "event_type": "application_started", + "message": "Application initialization completed successfully", + "details": {} + }, + { + "timestamp": "2025-08-28T12:59:39.115755", + "level": "info", + "event_type": "dataset_activated", + "message": "Dataset activated: DAR", + "details": { + "dataset_id": "DAR", + "variables_count": 5, + "streaming_count": 4, + "prefix": "dar" + } + }, + { + "timestamp": "2025-08-28T12:59:39.153973", + "level": "info", + "event_type": "csv_recording_started", + "message": "🔥 CRITICAL PRIORITY: CSV recording started with MAXIMUM PRIORITY, async buffering, and performance monitoring: 1 datasets activated", + "details": { + "activated_datasets": 1, + "total_datasets": 1, + "priority": "CRITICAL", + "recording_protection": true, + "performance_monitoring": true, + "async_csv_buffering": true, + "csv_flush_interval": 5.0 + } + }, + { + "timestamp": "2025-08-28T12:59:49.093323", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", + "details": { + "duration": 11.073070526123047, + "points_saved": 20, + "points_rate": 1.8061837457656371, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.0, + "cpu_max": 0.0, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.02772965431213379, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T12:59:59.123444", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 3.9% CPU", + "details": { + "duration": 10.030121326446533, + "points_saved": 20, + "points_rate": 1.9939938261031576, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 3.9, + "cpu_max": 3.9, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.026657521724700928, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:00:09.155956", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 19 points saved, 0 lost, 0.2% CPU", + "details": { + "duration": 10.032511472702026, + "points_saved": 19, + "points_rate": 1.8938428380269559, + "variables_saved": 95, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.2, + "cpu_max": 0.2, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.024308719133075914, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:00:19.189398", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 18 points saved, 4 lost, 0.3% CPU", + "details": { + "duration": 10.032859563827515, + "points_saved": 18, + "points_rate": 1.7941046503727835, + "variables_saved": 90, + "udp_points_sent": 0, + "points_lost": 4, + "cpu_average": 0.3, + "cpu_max": 0.3, + "delay_average": 2.017059326171875, + "delay_max": 2.017059326171875, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.17086312505933973, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:00:29.219344", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", + "details": { + "duration": 10.030528545379639, + "points_saved": 20, + "points_rate": 1.9939128740342, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.2, + "cpu_max": 0.2, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.028487110137939455, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:00:39.255486", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 19 points saved, 1 lost, 0.8% CPU", + "details": { + "duration": 10.035104990005493, + "points_saved": 19, + "points_rate": 1.8933533848348505, + "variables_saved": 95, + "udp_points_sent": 0, + "points_lost": 1, + "cpu_average": 0.8, + "cpu_max": 0.8, + "delay_average": 0.35400390625, + "delay_max": 0.35400390625, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.026340999101337633, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:00:49.286071", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", + "details": { + "duration": 10.031622171401978, + "points_saved": 20, + "points_rate": 1.9936955019115201, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.3, + "cpu_max": 0.3, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.026675033569335937, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:00:59.317363", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.6% CPU", + "details": { + "duration": 10.030781984329224, + "points_saved": 20, + "points_rate": 1.9938624955906104, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.6, + "cpu_max": 0.6, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.02779167890548706, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:01:09.359895", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", + "details": { + "duration": 10.042470455169678, + "points_saved": 20, + "points_rate": 1.9915418311939739, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.0, + "cpu_max": 0.0, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.028249919414520264, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:01:19.383922", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.6% CPU", + "details": { + "duration": 10.024598598480225, + "points_saved": 20, + "points_rate": 1.9950923524291628, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.6, + "cpu_max": 0.6, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.030459511280059814, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:01:29.416151", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.6% CPU", + "details": { + "duration": 10.032228708267212, + "points_saved": 20, + "points_rate": 1.9935749654031205, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.6, + "cpu_max": 0.6, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.026497554779052735, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:01:39.458122", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", + "details": { + "duration": 10.041424751281738, + "points_saved": 20, + "points_rate": 1.9917492283599594, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.3, + "cpu_max": 0.3, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.027211427688598633, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:01:49.488783", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", + "details": { + "duration": 10.0306978225708, + "points_saved": 20, + "points_rate": 1.9938792249325414, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.3, + "cpu_max": 0.3, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.027089643478393554, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:01:59.524926", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.6% CPU", + "details": { + "duration": 10.0366530418396, + "points_saved": 20, + "points_rate": 1.9926961624185264, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.6, + "cpu_max": 0.6, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.02756180763244629, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:02:09.559405", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.8% CPU", + "details": { + "duration": 10.034478664398193, + "points_saved": 20, + "points_rate": 1.9931279609930266, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.8, + "cpu_max": 0.8, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.028888785839080812, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:02:19.584864", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.5% CPU", + "details": { + "duration": 10.025458812713623, + "points_saved": 20, + "points_rate": 1.9949211675616605, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.5, + "cpu_max": 0.5, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.029392075538635255, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:02:29.611821", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.6% CPU", + "details": { + "duration": 10.026957511901855, + "points_saved": 20, + "points_rate": 1.994622992693475, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.6, + "cpu_max": 0.6, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.025148022174835204, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:02:39.688886", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 21 points saved, 0 lost, 0.6% CPU", + "details": { + "duration": 10.077064514160156, + "points_saved": 21, + "points_rate": 2.0839402159717326, + "variables_saved": 105, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.6, + "cpu_max": 0.6, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.03259219442095075, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:02:49.714125", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", + "details": { + "duration": 10.024601459503174, + "points_saved": 20, + "points_rate": 1.9950917830294685, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.0, + "cpu_max": 0.0, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.02601652145385742, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:02:59.753703", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.6% CPU", + "details": { + "duration": 10.03956151008606, + "points_saved": 20, + "points_rate": 1.9921188768959053, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.6, + "cpu_max": 0.6, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.027720987796783447, + "csv_write_time_avg": 5.054473876953125e-06 + } + }, + { + "timestamp": "2025-08-28T13:03:09.797715", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 1.1% CPU", + "details": { + "duration": 10.044666290283203, + "points_saved": 20, + "points_rate": 1.9911064660602191, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 1.1, + "cpu_max": 1.1, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.029020237922668456, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:25:08.140368", + "level": "info", + "event_type": "application_started", + "message": "Application initialization completed successfully", + "details": {} + }, + { + "timestamp": "2025-08-28T13:25:09.188176", + "level": "info", + "event_type": "application_started", + "message": "Application initialization completed successfully", + "details": {} + }, + { + "timestamp": "2025-08-28T13:26:21.556969", + "level": "info", + "event_type": "dataset_activated", + "message": "Dataset activated: DAR", + "details": { + "dataset_id": "DAR", + "variables_count": 5, + "streaming_count": 4, + "prefix": "dar" + } + }, + { + "timestamp": "2025-08-28T13:26:21.609135", + "level": "info", + "event_type": "csv_recording_started", + "message": "🔥 CRITICAL PRIORITY: CSV recording started with MAXIMUM PRIORITY, async buffering, and performance monitoring: 1 datasets activated", + "details": { + "activated_datasets": 1, + "total_datasets": 1, + "priority": "CRITICAL", + "recording_protection": true, + "performance_monitoring": true, + "async_csv_buffering": true, + "csv_flush_interval": 5.0 + } + }, + { + "timestamp": "2025-08-28T13:26:21.652428", + "level": "info", + "event_type": "plc_connection", + "message": "Successfully connected to PLC 10.1.33.11 and auto-started CSV recording for 1 datasets", + "details": { + "ip": "10.1.33.11", + "rack": 0, + "slot": 2, + "symbols_path": "C:/Users/migue/Downloads/symSAE452.asc", + "auto_started_recording": true, + "recording_datasets": 1, + "dataset_names": [ + "DAR" + ] + } + }, + { + "timestamp": "2025-08-28T13:26:31.554304", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", + "details": { + "duration": 83.37068605422974, + "points_saved": 20, + "points_rate": 0.2398924723612169, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.0, + "cpu_max": 0.0, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.027065014839172362, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:26:41.618842", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 21 points saved, 0 lost, 1.7% CPU", + "details": { + "duration": 10.064537286758423, + "points_saved": 21, + "points_rate": 2.086534075205723, + "variables_saved": 105, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 1.7, + "cpu_max": 1.7, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.027183998198736282, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:26:51.654972", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.8% CPU", + "details": { + "duration": 10.03613018989563, + "points_saved": 20, + "points_rate": 1.9927999758448718, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.8, + "cpu_max": 0.8, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.02952885627746582, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:27:01.683426", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.5% CPU", + "details": { + "duration": 10.028454542160034, + "points_saved": 20, + "points_rate": 1.9943252388410577, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.5, + "cpu_max": 0.5, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.026131439208984374, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:27:11.714001", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.5% CPU", + "details": { + "duration": 10.030068397521973, + "points_saved": 20, + "points_rate": 1.9940043484589993, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.5, + "cpu_max": 0.5, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.026390743255615235, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:27:21.758133", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.9% CPU", + "details": { + "duration": 10.044130563735962, + "points_saved": 20, + "points_rate": 1.991212666252011, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.9, + "cpu_max": 0.9, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.025641441345214844, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:29:47.187350", + "level": "info", + "event_type": "application_started", + "message": "Application initialization completed successfully", + "details": {} + }, + { + "timestamp": "2025-08-28T13:29:47.283160", + "level": "info", + "event_type": "dataset_activated", + "message": "Dataset activated: DAR", + "details": { + "dataset_id": "DAR", + "variables_count": 5, + "streaming_count": 4, + "prefix": "dar" + } + }, + { + "timestamp": "2025-08-28T13:29:47.319583", + "level": "info", + "event_type": "csv_recording_started", + "message": "🔥 CRITICAL PRIORITY: CSV recording started with MAXIMUM PRIORITY, async buffering, and performance monitoring: 1 datasets activated", + "details": { + "activated_datasets": 1, + "total_datasets": 1, + "priority": "CRITICAL", + "recording_protection": true, + "performance_monitoring": true, + "async_csv_buffering": true, + "csv_flush_interval": 5.0 + } + }, + { + "timestamp": "2025-08-28T13:29:48.373967", + "level": "info", + "event_type": "application_started", + "message": "Application initialization completed successfully", + "details": {} + }, + { + "timestamp": "2025-08-28T13:29:48.427849", + "level": "info", + "event_type": "dataset_activated", + "message": "Dataset activated: DAR", + "details": { + "dataset_id": "DAR", + "variables_count": 5, + "streaming_count": 4, + "prefix": "dar" + } + }, + { + "timestamp": "2025-08-28T13:29:48.456610", + "level": "info", + "event_type": "csv_recording_started", + "message": "🔥 CRITICAL PRIORITY: CSV recording started with MAXIMUM PRIORITY, async buffering, and performance monitoring: 1 datasets activated", + "details": { + "activated_datasets": 1, + "total_datasets": 1, + "priority": "CRITICAL", + "recording_protection": true, + "performance_monitoring": true, + "async_csv_buffering": true, + "csv_flush_interval": 5.0 + } + }, + { + "timestamp": "2025-08-28T13:29:58.421952", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.0% CPU", + "details": { + "duration": 11.054048538208008, + "points_saved": 20, + "points_rate": 1.8092918563610936, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.0, + "cpu_max": 0.0, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.028299331665039062, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:30:08.465139", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 21 points saved, 0 lost, 1.6% CPU", + "details": { + "duration": 10.042638063430786, + "points_saved": 21, + "points_rate": 2.0910840226801857, + "variables_saved": 105, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 1.6, + "cpu_max": 1.6, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.025419882365635464, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:30:18.489967", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.8% CPU", + "details": { + "duration": 10.025376319885254, + "points_saved": 20, + "points_rate": 1.9949375825753453, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.8, + "cpu_max": 0.8, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.026223647594451904, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:30:28.517177", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.5% CPU", + "details": { + "duration": 10.027210712432861, + "points_saved": 20, + "points_rate": 1.9945726257853298, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.5, + "cpu_max": 0.5, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.02555321455001831, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:30:38.546508", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", + "details": { + "duration": 10.028762102127075, + "points_saved": 20, + "points_rate": 1.9942640772940512, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.3, + "cpu_max": 0.3, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.026798701286315917, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:30:48.578334", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.3% CPU", + "details": { + "duration": 10.031788349151611, + "points_saved": 20, + "points_rate": 1.9936624761118888, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.3, + "cpu_max": 0.3, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.02890732288360596, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:30:58.603729", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.6% CPU", + "details": { + "duration": 10.026001214981079, + "points_saved": 20, + "points_rate": 1.994813243201641, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.6, + "cpu_max": 0.6, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.025467216968536377, + "csv_write_time_avg": 0.0 + } + }, + { + "timestamp": "2025-08-28T13:31:08.630350", + "level": "info", + "event_type": "performance_report", + "message": "Performance report: 20 points saved, 0 lost, 0.2% CPU", + "details": { + "duration": 10.026621341705322, + "points_saved": 20, + "points_rate": 1.9946898679429348, + "variables_saved": 100, + "udp_points_sent": 0, + "points_lost": 0, + "cpu_average": 0.2, + "cpu_max": 0.2, + "delay_average": 0.0, + "delay_max": 0.0, + "read_errors": 0, + "csv_errors": 0, + "udp_errors": 0, + "read_time_avg": 0.02825353145599365, + "csv_write_time_avg": 0.0 + } } ], - "last_updated": "2025-08-28T11:47:28.771992", + "last_updated": "2025-08-28T13:31:08.630350", "total_entries": 1000 } \ No newline at end of file diff --git a/core/plc_client.py b/core/plc_client.py index 62d3509..2549352 100644 --- a/core/plc_client.py +++ b/core/plc_client.py @@ -1128,3 +1128,64 @@ class PLCClient: self.logger.warning(f"Error getting batch reader stats: {e}") return base_stats + + def get_cpu_status(self) -> Dict[str, Any]: + """Get current CPU status including state and cycle time""" + if not self.is_connected(): + return {"connected": False, "error": "PLC not connected"} + + try: + # Get CPU state (RUN, STOP, etc.) + cpu_state = self.plc.get_cpu_state() + + # Get execution time (cycle time) + exec_time = self.plc.get_exec_time() + + # Get additional CPU info + cpu_info = self.plc.get_cpu_info() + + # Map CPU state codes to readable names + state_map = {0x08: "RUN", 0x04: "STOP", 0x00: "UNKNOWN"} + + # Safely handle cpu_state formatting + try: + # Try to get a readable state name + if isinstance(cpu_state, (int, bytes)): + if isinstance(cpu_state, bytes) and len(cpu_state) > 0: + cpu_state = cpu_state[0] + state_name = state_map.get(cpu_state, f"STATE_{cpu_state}") + else: + state_name = f"STATE_{str(cpu_state)}" + except Exception as e: + state_name = "UNKNOWN" + if self.logger: + self.logger.warning(f"Error parsing CPU state {cpu_state}: {e}") + + return { + "connected": True, + "state": state_name, + "state_code": cpu_state, + "cycle_time_ms": exec_time, + "cpu_info": { + "module_type_name": cpu_info.ModuleTypeName.decode( + "ascii", errors="ignore" + ).strip(), + "serial_number": cpu_info.SerialNumber.decode( + "ascii", errors="ignore" + ).strip(), + "as_name": cpu_info.ASName.decode("ascii", errors="ignore").strip(), + "module_name": cpu_info.ModuleName.decode( + "ascii", errors="ignore" + ).strip(), + "copyright": cpu_info.Copyright.decode( + "ascii", errors="ignore" + ).strip(), + }, + "timestamp": time.time(), + } + + except Exception as e: + error_msg = f"Error reading CPU status: {str(e)}" + if self.logger: + self.logger.error(error_msg) + return {"connected": True, "error": error_msg, "timestamp": time.time()} diff --git a/frontend/src/pages/Dashboard.jsx b/frontend/src/pages/Dashboard.jsx index 4305b40..4930e7e 100644 --- a/frontend/src/pages/Dashboard.jsx +++ b/frontend/src/pages/Dashboard.jsx @@ -701,12 +701,44 @@ function StatusBar({ status, isConnected, isLeader, connectionError }) { const [plotJugglerFound, setPlotJugglerFound] = useState(false) const [performanceData, setPerformanceData] = useState(null) const [performanceLoading, setPerformanceLoading] = useState(false) + const [cpuStatus, setCpuStatus] = useState(null) const toast = useToast() const setLoading = (action, loading) => { setActionLoading(prev => ({ ...prev, [action]: loading })) } + // Load CPU status data + const loadCpuStatus = useCallback(async () => { + if (!plcConnected) { + setCpuStatus(null) + return + } + + try { + const response = await api.getPlcStatus() + if (response.success && response.status) { + setCpuStatus(response.status) + } + } catch (error) { + // Silently fail - CPU status is optional + console.warn('Failed to load CPU status:', error) + setCpuStatus(null) + } + }, [plcConnected]) + + // Load CPU status when PLC is connected + useEffect(() => { + if (plcConnected && !connectionError) { + loadCpuStatus() + // Set up interval to refresh CPU status every 5 seconds + const interval = setInterval(loadCpuStatus, 5000) + return () => clearInterval(interval) + } else { + setCpuStatus(null) + } + }, [plcConnected, connectionError, loadCpuStatus]) + // Load performance data const loadPerformanceData = useCallback(async () => { if (!plcConnected || !csvRecording) { @@ -925,6 +957,28 @@ function StatusBar({ status, isConnected, isLeader, connectionError }) { + {/* CPU Status Card - Shows when PLC is connected */} + {plcConnected && cpuStatus && ( + + + + 🖥️ CPU Status + + {cpuStatus.state || 'UNKNOWN'} + + {cpuStatus.cycle_time_ms !== undefined && ( + + ⏱️ Cycle: {cpuStatus.cycle_time_ms}ms + {cpuStatus.cpu_info?.module_type_name && ( + <>
📟 {cpuStatus.cpu_info.module_type_name} + )} +
+ )} +
+
+
+ )} + diff --git a/frontend/src/services/api.js b/frontend/src/services/api.js index acdbcf8..a0f6433 100644 --- a/frontend/src/services/api.js +++ b/frontend/src/services/api.js @@ -363,4 +363,12 @@ export async function getHistoricalPerformance(windows = 6) { return toJsonOrThrow(res) } +// PLC Status API +export async function getPlcStatus() { + const res = await fetch(`${BASE_URL}/api/plc/status`, { + headers: { 'Accept': 'application/json' } + }) + return toJsonOrThrow(res) +} + diff --git a/main.py b/main.py index 755ff2f..383fcbc 100644 --- a/main.py +++ b/main.py @@ -2902,6 +2902,20 @@ def disable_plc_reconnection(): return jsonify({"success": False, "error": str(e)}), 500 +@app.route("/api/plc/status") +def get_plc_status(): + """Get current PLC CPU status including state and cycle time""" + error_response = check_streamer_initialized() + if error_response: + return error_response + + try: + status = streamer.plc_client.get_cpu_status() + return jsonify({"success": True, "status": status}) + except Exception as e: + return jsonify({"success": False, "error": str(e)}), 500 + + @app.route("/api/events") def get_events(): """Get recent events from the application log""" diff --git a/system_state.json b/system_state.json index 7c68642..f97e74f 100644 --- a/system_state.json +++ b/system_state.json @@ -7,6 +7,6 @@ ] }, "auto_recovery_enabled": true, - "last_update": "2025-08-28T11:46:10.725708", + "last_update": "2025-08-28T13:30:03.511773", "plotjuggler_path": "C:\\Program Files\\PlotJuggler\\plotjuggler.exe" } \ No newline at end of file