Files
GoProxy/CLAUDE.md
isboyjc f03c3300b4 feat: implement custom proxy subscription management and enhance configuration
- Added support for importing Clash/V2ray subscriptions, including automatic format detection and integration with sing-box for protocol conversion.
- Introduced five proxy usage modes in the configuration, allowing flexible selection between mixed, custom-only, and free-only modes.
- Enhanced `.env.example` and `docker-compose.yml` to include new environment variables for custom proxy settings.
- Updated `CHANGELOG.md` to document new features and improvements related to subscription management.
- Improved WebUI for managing subscriptions and displaying proxy statistics.
- Implemented a background process for refreshing subscriptions and probing disabled proxies for reactivation.
2026-04-04 22:25:54 +08:00

6.9 KiB

CLAUDE.md

This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.

Project Overview

GoProxy is an intelligent proxy pool system written in Go. It automatically fetches HTTP/SOCKS5 proxies from public sources, validates them (exit IP + geolocation + latency), and serves them via 4 proxy ports (HTTP random/stable, SOCKS5 random/stable) plus a WebUI dashboard.

Build & Run

# Run directly (requires Go 1.25, CGO enabled for sqlite3)
go run .

# Build and run
go build -o proxygo .
./proxygo

# Docker
docker compose up -d

CGO is required (CGO_ENABLED=1) because of the github.com/mattn/go-sqlite3 dependency.

Testing

There are no Go unit tests (go test ./...). Testing is done via shell scripts against a running instance:

# HTTP proxy test (continuous, Ctrl+C to stop)
./test/test_proxy.sh          # port 7777 (random)
./test/test_proxy.sh 7776     # port 7776 (stable)

# HTTP proxy HTTPS access test (random visits to Google/OpenAI/GitHub etc.)
./test/test_http_https.sh           # port 7777, continuous
./test/test_http_https.sh 7776 20   # port 7776, 20 iterations

# SOCKS5 proxy test
./test/test_socks5.sh localhost 7779      # random
./test/test_socks5.sh localhost 7780 50   # stable, 50 iterations

# Go/Python test scripts
go run test/test_proxy.go 7777
python test/test_proxy.py 7776

Architecture

The system is a single binary with several cooperating goroutines. Module go.mod name is goproxy.

Module Dependency Flow

main.go (orchestrator)
  ├── config/     — Global config (env vars + config.json), thread-safe singleton
  ├── storage/    — SQLite persistence layer (proxies + source_status tables)
  ├── fetcher/    — Multi-source proxy fetcher with circuit breaker (SourceManager)
  ├── validator/  — Concurrent proxy validation (connectivity + exit IP + geo + latency)
  ├── pool/       — Pool manager (admission control, slot allocation, replacement logic)
  ├── checker/    — Background health checker (batch-based, skips S-grade when healthy)
  ├── optimizer/  — Background quality optimizer (replaces slow proxies with faster ones)
  ├── custom/     — Custom proxy subscription manager (fetch, parse, validate, periodic refresh)
  │   ├── parser.go   — Clash YAML / plain / base64 subscription parser
  │   ├── singbox.go  — sing-box process manager (config generation, start/stop/reload)
  │   └── manager.go  — Subscription refresh loop + probe-wake loop for disabled proxies
  ├── proxy/      — Outward-facing proxy servers
  │   ├── server.go       — HTTP proxy (implements http.Handler)
  │   └── socks5_server.go — SOCKS5 proxy (raw TCP, manual protocol implementation)
  ├── webui/      — Dashboard server (embedded HTML in html.go, API in dashboard.go)
  └── logger/     — In-memory log collector for WebUI display

Key Design Patterns

  • Pool state machine: healthy → warning → critical → emergency. State determines fetch mode (optimize/refill/emergency) and latency thresholds.
  • Slot-based capacity: Pool has fixed size split between HTTP/SOCKS5 by configurable ratio (default 3:7). Each protocol has guaranteed minimum slots.
  • Smart admission: New proxies enter if slots available, or replace worst existing proxy if significantly faster (30%+ by default via ReplaceThreshold). HTTP proxies must also pass an HTTPS CONNECT tunnel test (random real HTTPS site visit with retry) before admission. Geo-filter (whitelist/blacklist) is applied during validation before admission.
  • Geo-filter: Whitelist (AllowedCountries) takes priority — if non-empty, only those countries pass. Otherwise blacklist (BlockedCountries) rejects listed countries. Configurable via env vars, config.json, or WebUI at runtime. On startup, existing proxies violating the filter are cleaned from the database.
  • Protocol-parallel validation: smartFetchAndFill splits candidates by protocol and validates SOCKS5/HTTP concurrently. SOCKS5 fills faster (no HTTPS check overhead); HTTP validation runs in parallel without blocking SOCKS5 admission.
  • Circuit breaker on sources: SourceManager tracks consecutive failures per source URL. 3 fails → degraded, 5 → disabled for 30min.
  • Auto-retry on proxy failure: Both HTTP and SOCKS5 servers retry with different upstream proxies on failure (up to MaxRetry times), deleting failed proxies immediately.
  • SOCKS5 service only uses SOCKS5 upstreams (many free HTTP proxies don't support CONNECT). HTTP service can use either protocol upstream.

Background Goroutines (started in main.go)

  1. Status monitor — every 30s, checks pool state and triggers smartFetchAndFill if needed
  2. Health checker — every HealthCheckInterval min, validates a batch of proxies
  3. Optimizer — every OptimizeInterval min, fetches from slow sources and replaces B/C grade proxies
  4. Config watcher — listens for WebUI config changes and adjusts pool slots

Ports

Port Service
7776 HTTP proxy (lowest-latency mode)
7777 HTTP proxy (random rotation mode)
7778 WebUI dashboard
7779 SOCKS5 proxy (random rotation mode)
7780 SOCKS5 proxy (lowest-latency mode)

Configuration

  • Environment variables: WEBUI_PASSWORD, PROXY_AUTH_ENABLED, PROXY_AUTH_USERNAME, PROXY_AUTH_PASSWORD, BLOCKED_COUNTRIES, ALLOWED_COUNTRIES, DATA_DIR
  • Persistent config: config.json (or $DATA_DIR/config.json) — pool capacity, latency thresholds, intervals, geo-filter (blocked/allowed countries). Editable via WebUI.
  • Config is loaded once at startup via config.Load(), updated in-memory via config.Save(). Thread-safe via sync.RWMutex.
  • Geo-filter: ALLOWED_COUNTRIES (whitelist) takes priority over BLOCKED_COUNTRIES (blacklist). When whitelist is non-empty, only listed countries are admitted; blacklist is ignored. Both are comma-separated country codes (e.g. US,JP,KR). Configurable at runtime via WebUI; config.json values override env vars after first save.

Storage

SQLite with MaxOpenConns(1) (single-writer). Two tables: proxies (with quality grades S/A/B/C based on latency) and source_status (circuit breaker state). Schema auto-migrates on startup.

WebUI

The entire frontend is embedded as Go string literals in webui/html.go. The server (webui/server.go) serves HTML and API endpoints. webui/dashboard.go contains API handlers. Dual-role auth: guest (read-only) and admin (full control via password).

Code Conventions

  • All log messages use [module] prefix: [pool], [fetch], [health], [optimize], [monitor], [socks5], [proxy], [tunnel], [storage], [source]
  • Comments and log messages are in Chinese
  • Quality grades: S (≤500ms), A (501-1000ms), B (1001-2000ms), C (>2000ms)
  • storage.Proxy is the shared data type across all modules