import asyncio import json import aiohttp import pytest from main import create_app, load_config @pytest.fixture async def app(): config = load_config() config["proxy_port"] = 8546 # Use different port for testing app = create_app(config) return app @pytest.fixture async def client(app, aiohttp_client): return await aiohttp_client(app) async def test_http_proxy_getBalance(client): """Test basic HTTP RPC request""" request_data = { "jsonrpc": "2.0", "id": 1, "method": "getBalance", "params": ["11111111111111111111111111111112"] # System program ID } async with client.post('/', json=request_data) as response: assert response.status == 200 data = await response.json() assert data["jsonrpc"] == "2.0" assert data["id"] == 1 assert "result" in data or "error" in data assert "_provider" in data assert data["_provider"] != "proxy_error" async def test_cache_functionality(client): """Test that responses are cached""" request_data = { "jsonrpc": "2.0", "id": 1, "method": "getBalance", "params": ["11111111111111111111111111111112"] } # First request async with client.post('/', json=request_data) as response: data1 = await response.json() provider1 = data1["_provider"] cached1 = data1["_cached"] # Second request (should be cached) async with client.post('/', json=request_data) as response: data2 = await response.json() provider2 = data2["_provider"] cached2 = data2["_cached"] # First request shouldn't be cached, second should be assert not cached1 assert cached2 assert provider2 == "cache" async def test_invalid_json_request(client): """Test invalid JSON handling""" async with client.post('/', data="invalid json") as response: assert response.status == 400 data = await response.json() assert "error" in data assert data["error"]["code"] == -32700 async def test_missing_method(client): """Test missing method handling""" request_data = { "jsonrpc": "2.0", "id": 1, "params": [] } async with client.post('/', json=request_data) as response: assert response.status == 400 data = await response.json() assert "error" in data assert data["error"]["code"] == -32600 async def test_websocket_connection(client): """Test WebSocket connection establishment""" try: async with client.ws_connect('/ws') as ws: # Send a simple subscription request subscribe_request = { "jsonrpc": "2.0", "id": 1, "method": "accountSubscribe", "params": [ "11111111111111111111111111111112", {"encoding": "jsonParsed"} ] } await ws.send_str(json.dumps(subscribe_request)) # Wait for response (with timeout) try: msg = await asyncio.wait_for(ws.receive(), timeout=10.0) if msg.type == aiohttp.WSMsgType.TEXT: response = json.loads(msg.data) assert "result" in response or "error" in response if "_provider" in response: assert response["_provider"] != "proxy_error" except asyncio.TimeoutError: # WebSocket might timeout if providers are unavailable # This is acceptable for the test pass except Exception as e: # WebSocket connection might fail if no providers are available # This is acceptable for testing environment pytest.skip(f"WebSocket test skipped due to provider unavailability: {e}") if __name__ == "__main__": # Run tests manually if executed directly import sys async def run_tests(): config = load_config() config["proxy_port"] = 8546 app = create_app(config) # Start the application runner = aiohttp.web.AppRunner(app) await runner.setup() site = aiohttp.web.TCPSite(runner, 'localhost', config["proxy_port"]) await site.start() print(f"Test server started on port {config['proxy_port']}") try: # Simple manual test async with aiohttp.ClientSession() as session: request_data = { "jsonrpc": "2.0", "id": 1, "method": "getBalance", "params": ["11111111111111111111111111111112"] } async with session.post( f"http://localhost:{config['proxy_port']}/", json=request_data ) as response: data = await response.json() print("Response:", json.dumps(data, indent=2)) # Test second request (should be cached) async with session.post( f"http://localhost:{config['proxy_port']}/", json=request_data ) as response: cached_data = await response.json() print("Cached response:", json.dumps(cached_data, indent=2)) except Exception as e: print(f"Test error: {e}") finally: await runner.cleanup() asyncio.run(run_tests())