diff --git a/app.py b/app.py index e7df157..7bd76f4 100644 --- a/app.py +++ b/app.py @@ -24,7 +24,7 @@ import rdm6300 # ============================================================================ # Server URLs -MONITORING_SERVER = "http://192.168.1.103:80/logs" +MONITORING_SERVER = "http://rpi-ansible:80/logs" HARTING_API_BASE = "https://dataswsibiusb01.sibiusb.harting.intra/RO_Quality_PRD/api/record" WIFI_CHECK_HOST = "10.76.140.17" @@ -139,7 +139,7 @@ def read_idmasa(): return "noconfig" def send_log_to_server(message, hostname, device_ip, name): - """Send log message to monitoring server""" + """Send log message to monitoring server with retry logic""" try: log_data = { "hostname": hostname, @@ -147,11 +147,36 @@ def send_log_to_server(message, hostname, device_ip, name): "nume_masa": name, "log_message": message } - response = requests.post(MONITORING_SERVER, json=log_data, timeout=5) - response.raise_for_status() - return True + logging.debug(f"[LOG] Sending to {MONITORING_SERVER}: {log_data}") + print(f"[LOG] Sending: {log_data}") + + # Try up to 3 times with small delay + for attempt in range(3): + try: + response = requests.post(MONITORING_SERVER, json=log_data, timeout=5) + response.raise_for_status() + logging.info(f"✓ Log sent to server: {message}") + print(f"✓ Log sent successfully") + return True + except (requests.exceptions.ConnectionError, requests.exceptions.Timeout) as e: + if attempt < 2: + time.sleep(1) # Wait 1 second before retry + continue + raise + + return False + + except requests.exceptions.Timeout: + logging.warning(f"✗ Log request timeout after retries: {message}") + print(f"✗ Timeout sending log") + return False + except requests.exceptions.ConnectionError as e: + logging.warning(f"✗ Connection error sending log: {e}") + print(f"✗ Connection error: {e}") + return False except Exception as e: - logging.warning(f"Failed to send log to server: {e}") + logging.warning(f"✗ Failed to send log to server: {e}") + print(f"✗ Failed to send log: {e}") return False def post_to_harting(url, verify=False, timeout=3): @@ -336,17 +361,24 @@ class RFIDReader(rdm6300.BaseReader): def process_card_events(hostname, device_ip): """Main thread checks card flags and processes them""" - name = read_idmasa() while True: try: + # Re-read name each time to catch configuration changes + name = read_idmasa() + # Check for inserted cards card_id, timestamp = card_state.get_inserted() if card_id is not None: logging.info(f"[Main] Processing CARD INSERTED: {card_id}") - # Skip posting to Harting API if device is not configured - if name != "noconfig": + if name == "noconfig": + # NOCONFIG MODE: Send card event directly to monitoring server + message = f"Card {card_id} inserted" + send_log_to_server(message, hostname, device_ip, name) + logging.info(f"✓ Card insert logged to monitoring: {message}") + else: + # CONFIGURED MODE: Try to post to Harting API first # Build API URL (1 = ON/inserted) url = f"{HARTING_API_BASE}/{name}/{card_id}/1/{timestamp}" @@ -362,16 +394,19 @@ def process_card_events(hostname, device_ip): f.write(url + "\n") except Exception as e: logging.error(f"Failed to save backup: {e}") - else: - logging.debug(f"Device not configured (noconfig). Skipping API post for card {card_id}") # Check for removed cards card_id, timestamp = card_state.get_removed() if card_id is not None: logging.info(f"[Main] Processing CARD REMOVED: {card_id}") - # Skip posting to Harting API if device is not configured - if name != "noconfig": + if name == "noconfig": + # NOCONFIG MODE: Send card event directly to monitoring server + message = f"Card {card_id} removed" + send_log_to_server(message, hostname, device_ip, name) + logging.info(f"✓ Card remove logged to monitoring: {message}") + else: + # CONFIGURED MODE: Try to post to Harting API first # Build API URL (0 = OFF/removed) url = f"{HARTING_API_BASE}/{name}/{card_id}/0/{timestamp}" @@ -387,8 +422,6 @@ def process_card_events(hostname, device_ip): f.write(url + "\n") except Exception as e: logging.error(f"Failed to save backup: {e}") - else: - logging.debug(f"Device not configured (noconfig). Skipping API post for card {card_id}") # Very small sleep for fast response (10ms = check 100x per second) time.sleep(0.01) @@ -608,6 +641,27 @@ def launch_chromium(name): print(f"✗ Failed to launch Chromium: {e}") logging.error(f"Failed to launch Chromium: {e}") +def send_health_status(hostname, device_ip): + """Send periodic health status messages when device is not configured""" + logging.info("Health status monitor started") + + while True: + try: + name = read_idmasa() + + # Only send health status when device is NOT configured + if name == "noconfig": + message = f"App working - RFID monitoring active" + send_log_to_server(message, hostname, device_ip, name) + logging.info(f"✓ Health check sent: {message}") + + # Send every 5 minutes + time.sleep(300) # 5 minutes + + except Exception as e: + logging.error(f"Error in health status monitor: {e}") + time.sleep(30) + # ============================================================================ # MAIN APPLICATION # ============================================================================ @@ -635,6 +689,10 @@ def main(): print(f"API: {HARTING_API_BASE}") print() + # Send startup message to monitoring server + name = read_idmasa() + send_log_to_server("App initialized", hostname, device_ip, name) + # Thread 1: Start RFID reader (background, listening for cards) rfid_reader = initialize_rfid_reader(hostname, device_ip) if not rfid_reader: @@ -642,6 +700,7 @@ def main(): logging.error("RFID reader initialization failed - exiting") sys.exit(1) print("✓ RFID reader started in background") + send_log_to_server("RFID initialized", hostname, device_ip, name) # Thread 2: Start card event processor (main thread checks flags and processes) card_processor_thread = threading.Thread( @@ -663,13 +722,23 @@ def main(): wifi_thread.start() print("✓ WiFi monitor started") + # Thread 4: Start health status monitor (sends periodic status when noconfig) + health_thread = threading.Thread( + target=send_health_status, + args=(hostname, device_ip), + daemon=False, + name="HealthMonitor" + ) + health_thread.start() + print("✓ Health status monitor started") + # Launch Chromium browser print("\nInitializing Chromium launcher...") time.sleep(2) # Give system time to stabilize launch_chromium(read_idmasa()) print() logging.info("RFID Client operational") - send_log_to_server("RFID Client operational", hostname, device_ip, read_idmasa()) + send_log_to_server("App working", hostname, device_ip, name) print("✓ RFID Client operational - waiting for cards...") print() diff --git a/data/log.txt b/data/log.txt index b1aa386..b259408 100644 Binary files a/data/log.txt and b/data/log.txt differ diff --git a/test_monitoring_server.py b/test_monitoring_server.py new file mode 100644 index 0000000..43618f8 --- /dev/null +++ b/test_monitoring_server.py @@ -0,0 +1,78 @@ +#!/usr/bin/env python3 +""" +Test script to verify connection to monitoring server +""" + +import requests +import socket +import sys + +# Configuration +MONITORING_SERVER = "http://rpi-ansible:80/logs" + +def test_connection(): + """Test if monitoring server is reachable""" + print(f"Testing connection to: {MONITORING_SERVER}\n") + + # Get local info + try: + hostname = socket.gethostname() + device_ip = socket.gethostbyname(hostname) + print(f"Local hostname: {hostname}") + print(f"Local IP: {device_ip}\n") + except Exception as e: + print(f"Error getting local info: {e}\n") + hostname = "unknown" + device_ip = "0.0.0.0" + + # Test 1: Simple GET request + print("1. Testing simple GET request...") + try: + response = requests.get(MONITORING_SERVER, timeout=5) + print(f" ✓ GET successful (Status: {response.status_code})") + print(f" Response: {response.text[:200]}\n") + except Exception as e: + print(f" ✗ GET failed: {e}\n") + + # Test 2: POST with test data + print("2. Testing POST with test data...") + try: + test_data = { + "hostname": hostname, + "device_ip": device_ip, + "nume_masa": "TEST_STATION", + "log_message": "Test message from client" + } + print(f" Payload: {test_data}") + response = requests.post(MONITORING_SERVER, json=test_data, timeout=5) + print(f" ✓ POST successful (Status: {response.status_code})") + print(f" Response: {response.text}\n") + except requests.exceptions.ConnectionError as e: + print(f" ✗ Connection error: {e}") + print(f" - Server may be unreachable at {MONITORING_SERVER}\n") + except requests.exceptions.Timeout: + print(f" ✗ Request timeout (5s)") + print(f" - Server may be offline or slow\n") + except Exception as e: + print(f" ✗ POST failed: {e}\n") + + # Test 3: Ping server IP + print("3. Testing network connectivity to server...") + import subprocess + try: + server_ip = "192.168.1.103" + result = subprocess.run( + ["ping", "-c", "1", server_ip], + stdout=subprocess.DEVNULL, + stderr=subprocess.DEVNULL, + timeout=5 + ) + if result.returncode == 0: + print(f" ✓ Server IP {server_ip} is reachable\n") + else: + print(f" ✗ Server IP {server_ip} is NOT reachable\n") + except Exception as e: + print(f" ✗ Ping failed: {e}\n") + +if __name__ == "__main__": + test_connection()