#!/usr/bin/env python3 """ Test script to verify UI flow works correctly. This tests: 1. API server is running 2. WebSocket connection works 3. Agent can be started via API 4. Events are broadcast properly """ import requests import json import time import websocket import threading API_URL = "http://localhost:8000" WS_URL = "ws://localhost:8000/ws" def test_api_server(): """Test if API server is running.""" print("๐Ÿ” Testing API server...") try: response = requests.get(f"{API_URL}/", timeout=5) if response.status_code == 200: data = response.json() print(f"โœ… API server is running: {data.get('service')}") print(f" Active connections: {data.get('active_connections')}") return True else: print(f"โŒ API server returned: {response.status_code}") return False except Exception as e: print(f"โŒ API server not accessible: {e}") return False def test_tools_endpoint(): """Test if tools endpoint works.""" print("\n๐Ÿ” Testing tools endpoint...") try: response = requests.get(f"{API_URL}/tools", timeout=5) if response.status_code == 200: data = response.json() toolsets = data.get("toolsets", []) print(f"โœ… Tools endpoint works - {len(toolsets)} toolsets available") for ts in toolsets[:3]: print(f" โ€ข {ts.get('name')} ({ts.get('tool_count')} tools)") return True else: print(f"โŒ Tools endpoint failed: {response.status_code}") return False except Exception as e: print(f"โŒ Tools endpoint error: {e}") return False def test_websocket(): """Test WebSocket connection.""" print("\n๐Ÿ” Testing WebSocket connection...") connected = threading.Event() message_received = threading.Event() messages = [] def on_open(ws): print("โœ… WebSocket connected") connected.set() def on_message(ws, message): data = json.loads(message) messages.append(data) message_received.set() print(f"๐Ÿ“จ Received: {data.get('event_type', 'unknown')}") def on_error(ws, error): print(f"โŒ WebSocket error: {error}") def on_close(ws, close_status_code, close_msg): print(f"๐Ÿ”Œ WebSocket closed: {close_status_code}") ws = websocket.WebSocketApp( WS_URL, on_open=on_open, on_message=on_message, on_error=on_error, on_close=on_close ) # Run WebSocket in background ws_thread = threading.Thread(target=lambda: ws.run_forever(), daemon=True) ws_thread.start() # Wait for connection if connected.wait(timeout=5): print("โœ… WebSocket connection established") ws.close() return True else: print("โŒ WebSocket connection timeout") ws.close() return False def test_agent_run(): """Test running agent via API.""" print("\n๐Ÿ” Testing agent run via API (mock mode)...") # Start listening for events first events = [] ws_connected = threading.Event() session_complete = threading.Event() def on_message(ws, message): data = json.loads(message) events.append(data) event_type = data.get("event_type") print(f" ๐Ÿ“จ Event: {event_type}") if event_type == "complete": session_complete.set() def on_open(ws): ws_connected.set() # Connect WebSocket ws = websocket.WebSocketApp( WS_URL, on_open=on_open, on_message=on_message ) ws_thread = threading.Thread(target=lambda: ws.run_forever(), daemon=True) ws_thread.start() # Wait for WebSocket connection if not ws_connected.wait(timeout=5): print("โŒ WebSocket didn't connect") ws.close() return False print("โœ… WebSocket connected, starting agent...") # Submit agent run payload = { "query": "Test query for UI flow verification", "model": "claude-sonnet-4-5-20250929", "base_url": "https://api.anthropic.com/v1/", "enabled_toolsets": ["web"], "max_turns": 5, "mock_web_tools": True, # Use mock mode to avoid API costs "mock_delay": 2, # Fast for testing "verbose": False } try: response = requests.post(f"{API_URL}/agent/run", json=payload, timeout=10) if response.status_code == 200: result = response.json() session_id = result.get("session_id") print(f"โœ… Agent started: {session_id[:8]}...") # Wait for completion (or timeout) print("โณ Waiting for agent to complete (up to 30s)...") if session_complete.wait(timeout=30): print(f"โœ… Agent completed! Received {len(events)} events:") # Count event types event_counts = {} for evt in events: evt_type = evt.get("event_type", "unknown") event_counts[evt_type] = event_counts.get(evt_type, 0) + 1 for evt_type, count in event_counts.items(): print(f" โ€ข {evt_type}: {count}") # Check we got expected events expected_events = ["query", "api_call", "response", "complete"] missing = [e for e in expected_events if e not in event_counts] if missing: print(f"โš ๏ธ Missing expected events: {missing}") else: print("โœ… All expected event types received!") ws.close() return True else: print(f"โš ๏ธ Timeout waiting for completion. Got {len(events)} events so far.") ws.close() return False else: print(f"โŒ Agent start failed: {response.status_code}") print(f" Response: {response.text}") ws.close() return False except Exception as e: print(f"โŒ Agent run error: {e}") import traceback traceback.print_exc() ws.close() return False def main(): """Run all tests.""" print("=" * 60) print("๐Ÿงช Hermes Agent UI Flow Test") print("=" * 60) print("\nThis will test the complete flow:") print(" 1. API server connectivity") print(" 2. Tools endpoint") print(" 3. WebSocket connection") print(" 4. Agent execution via API (mock mode)") print(" 5. Event streaming to UI") print("\n" + "=" * 60) results = [] # Test 1: API server results.append(("API Server", test_api_server())) # Test 2: Tools endpoint results.append(("Tools Endpoint", test_tools_endpoint())) # Test 3: WebSocket results.append(("WebSocket Connection", test_websocket())) # Test 4: Agent run results.append(("Agent Execution + Events", test_agent_run())) # Summary print("\n" + "=" * 60) print("๐Ÿ“Š TEST SUMMARY") print("=" * 60) for test_name, passed in results: status = "โœ… PASS" if passed else "โŒ FAIL" print(f"{status} - {test_name}") all_passed = all(r[1] for r in results) print("\n" + "=" * 60) if all_passed: print("๐ŸŽ‰ ALL TESTS PASSED!") print("\nโœ… The UI flow is working correctly!") print(" You can now use the UI to:") print(" โ€ข Submit queries") print(" โ€ข View real-time events") print(" โ€ข See tool executions") print(" โ€ข Get final responses") else: print("โŒ SOME TESTS FAILED") print("\nMake sure:") print(" 1. API server is running: python api_endpoint/logging_server.py") print(" 2. ANTHROPIC_API_KEY is set in environment") print(" 3. All dependencies are installed: pip install -r requirements.txt") print("=" * 60) return 0 if all_passed else 1 if __name__ == "__main__": exit(main())