# How to Fix Python TimeoutError
The TimeoutError occurs when an operation takes longer than the allowed time limit. This can happen with network operations, file I/O, threading, or any operation that has a timeout constraint.
Error Patterns
Socket Timeout
Traceback (most recent call last):
File "app.py", line 5, in <module>
socket.recv(1024)
socket.timeout: timed outRequest Timeout
Traceback (most recent call last):
File "app.py", line 10, in <module>
requests.get(url, timeout=5)
requests.exceptions.Timeout: HTTPConnectionPool(host='slow.example.com'): Read timed out.Connection Timeout
Traceback (most recent call last):
File "app.py", line 15, in <module>
socket.connect((host, port))
TimeoutError: [Errno 110] Connection timed outLock Timeout
Traceback (most recent call last):
File "app.py", line 20, in <module>
lock.acquire(timeout=5)
TimeoutError: Lock acquisition timed outCommon Causes
- 1.Slow server response - Server takes longer than timeout to respond
- 2.Network latency - High network delays
- 3.Server overload - Server processing many requests
- 4.Large data transfer - Transferring large files with short timeout
- 5.DNS resolution delay - DNS lookup taking too long
- 6.Resource contention - Waiting for locks or resources
- 7.Infinite loops - Code stuck in processing loop
- 8.Firewall blocking silently - Connection drops without response
Diagnosis Steps
Step 1: Check Timeout Setting
```python import socket import requests
# Check current timeout settings sock = socket.socket() print(f"Default socket timeout: {sock.gettimeout()}") # None means no timeout
# For requests response = requests.get(url) print(f"Request timeout used: {response.elapsed.total_seconds()}s") ```
Step 2: Test Server Response Time
```python import time import requests
def measure_response_time(url): """Measure how long server takes to respond.""" start = time.time() try: response = requests.get(url, timeout=None) # No timeout elapsed = time.time() - start print(f"Response time: {elapsed:.2f}s") return elapsed except Exception as e: elapsed = time.time() - start print(f"Failed after {elapsed:.2f}s: {e}") return None
measure_response_time("https://example.com/api") ```
Step 3: Check Network Connectivity
```bash # Test network latency ping example.com
# Check connection time time curl -s https://example.com
# Trace network path traceroute example.com # Linux/Mac tracert example.com # Windows ```
Step 4: Monitor Resource Usage
```python import threading import time
def monitor_blocking_operation(func, timeout=5): """Monitor function execution time.""" result = {"completed": False, "time": 0, "error": None}
def wrapper(): start = time.time() try: result["value"] = func() result["completed"] = True except Exception as e: result["error"] = e result["time"] = time.time() - start
thread = threading.Thread(target=wrapper) thread.start() thread.join(timeout)
if not result["completed"]: print(f"Operation timed out after {timeout}s")
return result ```
Solutions
Solution 1: Increase Timeout Value
```python import socket import requests
# Problem: Timeout too short for operation sock.settimeout(1) # 1 second timeout data = sock.recv(1024) # May timeout for slow server
# Fix: Increase timeout sock.settimeout(30) # 30 second timeout data = sock.recv(1024) # More time for slow server
# For requests response = requests.get(url, timeout=5) # Short timeout
# Fix: Increase timeout response = requests.get(url, timeout=30) # Longer timeout
# Or use tuple for separate connect/read timeouts response = requests.get(url, timeout=(3, 30)) # 3s connect, 30s read ```
Solution 2: Handle Timeout Exception
```python import socket import requests from requests.exceptions import Timeout
def safe_request(url, timeout=10, retries=3): """Make request with timeout handling.""" for attempt in range(retries): try: response = requests.get(url, timeout=timeout) return response except Timeout: print(f"Request timed out (attempt {attempt + 1}/{retries})") if attempt < retries - 1: continue # Retry raise # Raise after all retries failed return None
# Socket example def safe_recv(sock, timeout=10, retries=3): """Receive data with timeout handling.""" sock.settimeout(timeout)
for attempt in range(retries): try: data = sock.recv(1024) return data except socket.timeout: print(f"Receive timed out (attempt {attempt + 1}/{retries})") if attempt < retries - 1: continue raise return None ```
Solution 3: Use Non-blocking Operations
```python import socket import select
# Problem: Blocking socket operation sock.setblocking(True) # Blocks until data available data = sock.recv(1024) # May block indefinitely
# Fix: Use non-blocking mode sock.setblocking(False)
try: data = sock.recv(1024) except socket.error as e: if e.errno == 11: # Resource temporarily unavailable # No data available yet data = None else: raise
# Or use select for controlled waiting sock.setblocking(False) ready = select.select([sock], [], [], 5) # Wait up to 5s
if ready[0]: # Data available data = sock.recv(1024) else: print("Timeout - no data received") data = None ```
Solution 4: Implement Async Operations
```python import asyncio import aiohttp
async def async_request(url, timeout=30): """Make async HTTP request.""" timeout_config = aiohttp.ClientTimeout(total=timeout)
async with aiohttp.ClientSession(timeout=timeout_config) as session: try: async with session.get(url) as response: return await response.text() except asyncio.TimeoutError: print(f"Request timed out after {timeout}s") return None
# Run async function result = asyncio.run(async_request("https://example.com", timeout=10))
# Socket async async def async_recv(host, port, timeout=10): """Async socket receive.""" try: reader, writer = await asyncio.wait_for( asyncio.open_connection(host, port), timeout=timeout ) data = await asyncio.wait_for(reader.read(1024), timeout=timeout) writer.close() await writer.wait_closed() return data except asyncio.TimeoutError: print("Connection or read timed out") return None ```
Solution 5: Use Threading with Timeout
```python import threading import time
def run_with_timeout(func, timeout, *args): """Run function with timeout constraint.""" result = [None] exception = [None]
def worker(): try: result[0] = func(*args) except Exception as e: exception[0] = e
thread = threading.Thread(target=worker) thread.start() thread.join(timeout)
if thread.is_alive(): # Thread is still running - timed out print(f"Function timed out after {timeout}s") return None, TimeoutError(f"Operation timed out after {timeout}s")
if exception[0]: return None, exception[0]
return result[0], None
# Usage result, error = run_with_timeout(slow_function, 5, arg1, arg2) if error: print(f"Error: {error}") else: print(f"Result: {result}") ```
Solution 6: Optimize Data Transfer
```python import socket
# Problem: Large data with short timeout sock.settimeout(5) # 5 seconds data = sock.recv(1024*1024) # Trying to receive 1MB
# Fix: Receive in chunks sock.settimeout(5)
def recv_all(sock, size, chunk_size=8192): """Receive large data in chunks.""" data = b'' while len(data) < size: chunk = sock.recv(min(chunk_size, size - len(data))) if not chunk: break data += chunk return data
# Or stream processing def stream_response(url, chunk_size=8192, timeout=30): """Stream large response.""" import requests response = requests.get(url, timeout=timeout, stream=True)
for chunk in response.iter_content(chunk_size=chunk_size): process_chunk(chunk) ```
Solution 7: Use Retry with Increasing Timeout
```python import time import requests
def exponential_backoff_request(url, max_retries=5, base_timeout=5): """Request with exponential backoff.""" timeout = base_timeout
for attempt in range(max_retries): try: response = requests.get(url, timeout=timeout) return response except requests.exceptions.Timeout: if attempt < max_retries - 1: # Increase timeout exponentially timeout = base_timeout * (2 ** attempt) print(f"Retry {attempt + 1} with timeout {timeout}s") time.sleep(1) # Wait before retry else: raise
return None
# Usage response = exponential_backoff_request( "https://slow.example.com", max_retries=5, base_timeout=5 ) ```
Solution 8: Handle Specific Timeout Types
```python import requests from requests.exceptions import ConnectTimeout, ReadTimeout
def handle_timeout_types(url, connect_timeout=5, read_timeout=30): """Handle different timeout types.""" try: response = requests.get( url, timeout=(connect_timeout, read_timeout) ) return response
except ConnectTimeout: print(f"Connection timeout after {connect_timeout}s") print("Possible causes:") print(" - Server unreachable") print(" - DNS resolution slow") print(" - Firewall blocking") # Maybe retry with longer connect timeout return None
except ReadTimeout: print(f"Read timeout after {read_timeout}s") print("Possible causes:") print(" - Server processing slow") print(" - Large response") print(" - Server overloaded") # Maybe retry with longer read timeout return None
except requests.exceptions.Timeout: print("General timeout error") return None
# Usage response = handle_timeout_types( "https://api.example.com", connect_timeout=5, read_timeout=30 ) ```
Timeout Best Practices
Appropriate Timeout Values
```python # Typical timeout recommendations:
# Fast API calls timeout = 5 # 5 seconds
# Database queries timeout = 30 # 30 seconds
# File uploads timeout = 60 # 60 seconds per MB
# Large downloads timeout = None # No timeout, use streaming
# Connection establishment connect_timeout = 10 # 10 seconds
# Health checks timeout = 3 # 3 seconds
# Background tasks timeout = 300 # 5 minutes ```
Socket Timeout Configuration
```python import socket
def create_socket_with_timeout(host, port, connect_timeout=5, recv_timeout=30): """Create socket with proper timeout settings.""" sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
# Set connect timeout sock.settimeout(connect_timeout)
try: sock.connect((host, port))
# Change to receive timeout after connection sock.settimeout(recv_timeout)
return sock
except socket.timeout: sock.close() raise TimeoutError(f"Connection to {host}:{port} timed out") ```
Common Timeout Patterns
Web Scraping with Timeout
```python import requests from requests.adapters import HTTPAdapter from urllib3.util.retry import Retry
def create_session_with_timeout(total_timeout=30): """Create requests session with timeout and retry.""" session = requests.Session()
# Retry strategy retry = Retry( total=3, backoff_factor=1, status_forcelist=[500, 502, 503, 504] )
adapter = HTTPAdapter(max_retries=retry) session.mount('http://', adapter) session.mount('https://', adapter)
# Set default timeout def request_with_timeout(method, url, **kwargs): kwargs.setdefault('timeout', total_timeout) return session.request(method, url, **kwargs)
session.request = request_with_timeout return session ```
Database Connection Timeout
```python import psycopg2
def connect_postgresql_with_timeout(host, port, timeout=10): """Connect to PostgreSQL with timeout.""" # Note: psycopg2 uses tcp_keepalives for timeout conn = psycopg2.connect( host=host, port=port, connect_timeout=timeout, # Connection timeout options='-c statement_timeout=30000' # Query timeout 30s ) return conn
# Or use async import asyncpg
async def async_pg_connect(host, port, timeout=10): conn = await asyncpg.connect( host=host, port=port, timeout=timeout ) return conn ```
Prevention Tips
- 1.Set appropriate timeouts based on expected operation time
- 2.Use retry logic with exponential backoff
- 3.Separate connect and read timeouts for network operations
- 4.Use streaming for large data transfers
- 5.Implement health checks to detect slow services
```python # Good pattern: Comprehensive timeout handling def safe_operation(host, port, timeout=30, retries=3): """Perform operation with timeout handling.""" for attempt in range(retries): try: sock = socket.create_connection((host, port), timeout=timeout) sock.settimeout(timeout)
# Perform operation result = perform_operation(sock)
sock.close() return result
except socket.timeout: print(f"Timeout (attempt {attempt + 1}/{retries})") if attempt < retries - 1: time.sleep(2 ** attempt) # Exponential backoff continue
except TimeoutError: print(f"Timeout error (attempt {attempt + 1}/{retries})") continue
raise TimeoutError(f"Operation failed after {retries} attempts") ```
Related Errors
ConnectionRefusedError- Connection rejectedsocket.timeout- Socket-specific timeoutasyncio.TimeoutError- Async operation timeoutrequests.exceptions.Timeout- Requests library timeout