Tor's fastest rotating proxy. Torque distributes new HTTP/HTTPS streams across a warm pool of managed Tor circuits.
- Best-effort IP rotation with exit diversity, health, capacity, and recent usage taken into account
- Target-aware circuit burning that replaces exits rejected by a configured HTTPS endpoint
- HTTP, HTTPS, and WebSocket proxying through standard requests, protocol upgrades, and
CONNECTtunnels - Sticky sessions with the
Proxy-Torque-Sessionheader - Bounded resource usage with rate, queue, bandwidth, circuit, and concurrency limits
- Production controls including authentication, TLS, destination policies, health checks, and Prometheus metrics
- Ready-to-run deployments for Docker, Docker Compose, and Kubernetes
docker run -d --rm \
--name torque \
-p 127.0.0.1:3128:3128 \
ghcr.io/g0ldyy/torque:latestWait until the container is healthy, then point any HTTP client at 127.0.0.1:3128:
docker inspect -f '{{.State.Health.Status}}' torque
curl --proxy http://127.0.0.1:3128 https://api.ipify.org
docker exec torque torque statusThe bundled rotate-20rps profile starts two Tor shards and targets 32 ready circuits. Startup can take a few minutes while Tor bootstraps and builds the initial pool.
Warning
The default profile is anonymous. Keep the explicit 127.0.0.1 port binding; publishing 3128 on every interface would expose an open proxy.
Torque selects a managed circuit for every new proxy stream and avoids the previously selected exit whenever another healthy exit is available. Rotation is best effort: Tor has a finite exit set, so a globally unique IP for every request cannot be guaranteed.
Plain HTTP requests create new streams. HTTPS requests sharing one CONNECT tunnel also share its circuit and IP; open a new proxy connection when every request must rotate.
To deliberately reuse a circuit for up to ten minutes:
curl \
--proxy http://127.0.0.1:3128 \
--proxy-header 'Proxy-Torque-Session: account-42' \
https://api.ipify.orgDocker Compose applies the hardened runtime settings and preserves Tor guard state in a named volume:
docker compose -f deploy/compose.yaml up -d --wait --wait-timeout 300Kubernetes uses the same preset with a private ClusterIP, persistent guard state, and a restrictive NetworkPolicy:
kubectl apply -k deploy
kubectl -n torque rollout status statefulset/torque --timeout=5m
kubectl -n torque port-forward service/torque 3128:3128Label other trusted client namespaces with torque.g0ldyy/client=true before allowing them through the policy.
The configuration guide and complete reference
documents every TOML setting, its default, validation constraints, reload
behavior, credentials, destination policy, and the target-aware burner.
configs/torque.example.toml is a complete
starting point, and ready-made capacity profiles live in
configs/profiles.
Mount a custom configuration into the container:
docker run --rm \
-p 127.0.0.1:3128:3128 \
--mount type=bind,src="$PWD/torque.toml",dst=/etc/torque/custom.toml,readonly \
ghcr.io/g0ldyy/torque:latest \
-config /etc/torque/custom.tomlRemote deployments should enable TLS and hashed proxy credentials. Admin and metrics endpoints are private by default.
go test -race ./...
docker build -f deploy/Dockerfile -t torque:local .Released under the GNU General Public License v3.0.