"""Bounded PROXY-v1 parser and trusted reverse-proxy client-IP extraction.""" import ipaddress CLIENT_HEADERS = ('CF-Connecting-IP', 'True-Client-IP', 'X-Real-IP') def public_ip(value): """Return a normalized global client IP, or None for private/spoofed values.""" try: ip = ipaddress.ip_address(value.strip()) except (ValueError, AttributeError): return None if not ip.is_global or ip.is_multicast: return None return str(ip) def forwarded_client(headers): """Real client IP from a trusted proxy. Priority: single-hop headers, then nearest XFF hop.""" for name in CLIENT_HEADERS: value = headers.get(name) if value: ip = public_ip(value) if ip: return ip, name for hop in reversed((headers.get('X-Forwarded-For') or '').split(',')): ip = public_ip(hop) if ip: return ip, 'X-Forwarded-For' return None, None def source(connection, transport, trusted): if transport[0] != trusted: raise ValueError('untrusted PROXY transport') header = bytearray() while len(header) < 108: value = connection.recv(1) if not value: raise ValueError('incomplete PROXY header') header.extend(value) if header.endswith(b'\r\n'): break else: raise ValueError('oversize PROXY header') fields = header.decode('ascii').strip().split(' ') if len(fields) != 6 or fields[0] != 'PROXY' or fields[1] not in ('TCP4', 'TCP6'): raise ValueError('invalid PROXY header') version = 4 if fields[1] == 'TCP4' else 6 if any(ipaddress.ip_address(ip).version != version for ip in fields[2:4]): raise ValueError('PROXY address family mismatch') ports = [int(value) for value in fields[4:]] if any(not 0 < port <= 65535 for port in ports): raise ValueError('invalid PROXY port') return (fields[2], ports[0]), bytes(header)