python-socks

Core SOCKS4, SOCKS5, and HTTP CONNECT proxy client for Python with sync and async APIs

Library
PyPI
v3.0.0
126stars
Apache License 2.0

Repository Health

Pre-computed score based on development activity, maintenance, community, maturity, and trend momentum.How we score it →
69/100Good
Development Activity60
Maintenance76
Community60
Maturity60
Momentum20

Technical Analysis

AI-assessed by reading the actual repository — architecture, code quality, innovation, and documentation.How we score it →
75/100Good
Architecture82
Code Quality88
Innovation84
Learning Curve45

python-socks provides the core proxy-client protocol implementation for SOCKS4(a), SOCKS5(h), and HTTP CONNECT proxies in Python, with matching sync and async APIs for asyncio, trio, and anyio. Rather than bundling its own HTTP stack, it hands back a plain socket (or async stream) once the proxy handshake completes, so it slots underneath whatever transport layer — urllib3, aiohttp, httpx, or raw sockets — a project already uses.

It’s the shared connector library behind romis2012’s own aiohttp-socks and httpx-socks packages, and supports proxy chaining (routing a connection through multiple proxies in sequence) and remote DNS resolution through the proxy (rdns) out of the box.

What You Get

  • A single Proxy.from_url() constructor across all four backends (sync, asyncio, trio, anyio) that parses standard socks5://user:pass@host:port proxy URLs.
  • Full protocol coverage for SOCKS4(a), SOCKS5(h), and HTTP CONNECT, including username/password auth and remote-DNS (rdns) resolution.
  • Proxy chaining via the forward= parameter, letting you route a connection through multiple proxies in sequence.
  • A typed error hierarchy (ProxyError, ProxyConnectionError, ProxyTimeoutError) so callers can catch proxy-specific failures distinctly from generic socket errors.
  • A py.typed marker and full mypy coverage, so downstream type checkers see accurate signatures.

Common Use Cases

  • Adding SOCKS/HTTP proxy support to an existing HTTP client (urllib3, requests, aiohttp, httpx) without reimplementing the handshake.
  • Routing traffic through a chain of proxies for layered anonymization or network segmentation.
  • Building a custom async network client (asyncio, trio, or anyio) that needs to connect out through a corporate or residential proxy.
  • Testing proxy-aware application code against a local SOCKS/HTTP proxy in CI.

Under The Hood

Architecture python_socks/_abc.py defines abstract SyncResolver/AsyncResolver and SyncSocketStream/AsyncSocketStream base classes that every backend depends on. The connectors/ package (factory_sync.py, factory_async.py) implements protocol-specific handshake logic per proxy type (socks4_sync.py, socks5_sync.py, http_sync.py and their async counterparts) built on shared wire-framing logic in protocols/socks4.py, socks5.py, and http.py. Each concurrency-specific Proxy class (SyncProxy in sync/proxy.py, and the analogous classes under async/asyncio, async/trio, async/anyio) composes a resolver, a stream, and a connector selected via create_connector() and a ProxyType enum, and supports proxy chaining by recursively calling connect() through a forward proxy. A newer sync/v2/ variant (with its own _ssl_transport.py) sits alongside the original sync implementation, showing incremental architecture evolution rather than a rewrite. This is a modular, protocol-per-connector design: adding a new proxy type means adding a connector and protocol module without touching the Proxy classes themselves, since every connector depends on the same narrow stream interface.

Tech Stack Pure Python (100%) with no required runtime dependencies; async-timeout (<3.11), trio>=0.30, and anyio>=4.12 are gated behind optional extras in pyproject.toml. The build backend is setuptools>=77 with the version read dynamically from python_socks.version. Dev tooling is managed with uv (uv.lock is checked in), ruff handles linting and formatting against a near-full ruleset with targeted ignores, mypy provides static type checking against the shipped py.typed package, and pytest with pytest-asyncio/pytest-trio/pytest-cov drives testing, backed by tiny-proxy and trustme as test-only proxy/TLS fixtures and starlette+uvicorn to run a real HTTP server for integration-style tests. CI (.github/workflows/ci.yml) runs ruff check/format, mypy, and pytest-cov across Python 3.9–3.14 on ubuntu-latest with Codecov upload.

Code Quality tests/ mirrors every backend with its own module (test_proxy_sync.py, test_proxy_sync_v2.py, test_proxy_async_aio.py/_v2.py, test_proxy_async_anyio.py/_v2.py, test_proxy_async_trio.py/_v2.py) plus test_resolvers.py and test_misc.py, exercising the same behavior across each concurrency model to catch drift between them. Fixtures spin up real proxy_server.py and http_server.py instances via starlette/uvicorn rather than mocking sockets, giving realistic coverage of actual SOCKS4/5/HTTP handshakes. Error handling is explicit and typed through a dedicated _errors.py hierarchy that callers can catch specifically instead of swallowing generic exceptions. Naming is consistent (leading-underscore for internal modules, explicit public re-exports in init.py), and the package ships a py.typed marker with mypy enforcement in CI. Inline comments are sparse relative to the codebase size, leaning on type signatures and naming for self-documentation instead.

API Design Proxy.from_url() parses a standard proxy URL string (e.g. socks5://user:pass@host:port) into a ready-to-use client in one call across all four backends, and every backend (sync, asyncio, trio, anyio) exposes an identical constructor and connect() signature, so switching concurrency models is a one-line import change. Proxy chaining is exposed through a single forward= constructor argument rather than a separate chaining API. The README documents every backend with runnable end-to-end examples, including a urllib3 PoolManager integration recipe and a proxy-chaining example. The one deliberate boilerplate cost is that connect() returns a raw socket or stream rather than wrapping TLS itself, so callers handle SSL wrapping explicitly — consistent with the library’s narrow, composable scope.

Join founders buildingwith open source

Opinionated takes, migration guides, cost-saving tips, and insights from the open source ecosystem.

Subscribe on Substack
Join 750+ subscribers

Search