feat: 代理提取接口支持 fmt=url——返回握手实测协议的 scheme://ip:port

proxyx.Check 改回返回胜出协议名(socks5/socks4/http),提取接口加 fmt=url
时输出 socks5h:// / http:// / socks4:// 完整代理 URL(socks5h 让 DNS 走代理端),
供 auto-registr 这类需要带 scheme 的消费端直接使用;默认 ip:port 行为不变。

Generated with [Devin](https://devin.ai)

Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
This commit is contained in:
2026-10-08 19:37:50 +08:00
co-authored by Devin
parent fa6ab5d3c7
commit c0a24faf8e
5 changed files with 39 additions and 19 deletions
+6 -4
View File
@@ -271,11 +271,13 @@ const probeHost = "www.gstatic.com"
const probePort = 80
// Check 协议感知测活:按 protocols 依次尝试 SOCKS5/SOCKS4/HTTP 握手,
// 纯 TCP 连通不算数——必须说出协议正确的应答才算活。返回拨测耗时。
func Check(ctx context.Context, ip string, port int, protocols string, timeout time.Duration) (int, error) {
// 纯 TCP 连通不算数——必须说出协议正确的应答才算活。
// 返回握手成功的协议名(socks5/socks4/http)与拨测耗时。
func Check(ctx context.Context, ip string, port int, protocols string, timeout time.Duration) (string, int, error) {
probes := []func(context.Context, string, int, time.Duration) error{
probeSOCKS5, probeSOCKS4, probeHTTP,
}
names := []string{"socks5", "socks4", "http"}
upper := strings.ToUpper(protocols)
order := []int{}
for i, name := range []string{"SOCKS5", "SOCKS4", "HTTP"} {
@@ -290,12 +292,12 @@ func Check(ctx context.Context, ip string, port int, protocols string, timeout t
for _, i := range order {
start := time.Now()
if err := probes[i](ctx, ip, port, timeout); err == nil {
return int(time.Since(start).Milliseconds()), nil
return names[i], int(time.Since(start).Milliseconds()), nil
} else {
lastErr = err
}
}
return 0, lastErr
return "", 0, lastErr
}
func dial(ctx context.Context, ip string, port int, timeout time.Duration) (net.Conn, error) {