mirror of
https://github.com/NoFxAiOS/nofx.git
synced 2026-07-13 07:46:54 +08:00
feat(proxy): add proxy module
This commit is contained in:
105
proxy/brightdata_provider.go
Normal file
105
proxy/brightdata_provider.go
Normal file
@@ -0,0 +1,105 @@
|
||||
package proxy
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"io/ioutil"
|
||||
"net/http"
|
||||
"time"
|
||||
)
|
||||
|
||||
// BrightDataProvider Bright Data动态获取IP提供者
|
||||
type BrightDataProvider struct {
|
||||
endpoint string
|
||||
token string
|
||||
zone string
|
||||
client *http.Client
|
||||
}
|
||||
|
||||
// NewBrightDataProvider 创建Bright Data IP提供者
|
||||
func NewBrightDataProvider(endpoint, token, zone string) *BrightDataProvider {
|
||||
return &BrightDataProvider{
|
||||
endpoint: endpoint,
|
||||
token: token,
|
||||
zone: zone,
|
||||
client: &http.Client{
|
||||
Timeout: 30 * time.Second,
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
// BrightDataIPList Bright Data API返回的IP列表结构
|
||||
type BrightDataIPList struct {
|
||||
IPs []struct {
|
||||
IP string `json:"ip"`
|
||||
Maxmind string `json:"maxmind"`
|
||||
Ext map[string]interface{} `json:"ext"`
|
||||
} `json:"ips"`
|
||||
}
|
||||
|
||||
func (p *BrightDataProvider) GetIPList() ([]ProxyIP, error) {
|
||||
return p.fetchIPList()
|
||||
}
|
||||
|
||||
func (p *BrightDataProvider) RefreshIPList() ([]ProxyIP, error) {
|
||||
return p.fetchIPList()
|
||||
}
|
||||
|
||||
func (p *BrightDataProvider) fetchIPList() ([]ProxyIP, error) {
|
||||
// 构建请求URL
|
||||
url := p.endpoint
|
||||
if p.zone != "" {
|
||||
url = fmt.Sprintf("%s?zone=%s", p.endpoint, p.zone)
|
||||
}
|
||||
|
||||
// 创建HTTP请求
|
||||
req, err := http.NewRequest("GET", url, nil)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("创建HTTP请求失败: %w", err)
|
||||
}
|
||||
|
||||
// 设置授权头
|
||||
if p.token != "" {
|
||||
req.Header.Set("Authorization", fmt.Sprintf("Bearer %s", p.token))
|
||||
}
|
||||
|
||||
// 发送请求
|
||||
resp, err := p.client.Do(req)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("发送HTTP请求失败: %w", err)
|
||||
}
|
||||
defer resp.Body.Close()
|
||||
|
||||
// 读取响应体
|
||||
body, err := ioutil.ReadAll(resp.Body)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("读取HTTP响应失败: %w", err)
|
||||
}
|
||||
|
||||
// 检查状态码
|
||||
if resp.StatusCode != http.StatusOK {
|
||||
return nil, fmt.Errorf("API返回错误状态码 %d: %s", resp.StatusCode, string(body))
|
||||
}
|
||||
|
||||
// 解析JSON数据(支持Bright Data格式)
|
||||
var ipList BrightDataIPList
|
||||
if err := json.Unmarshal(body, &ipList); err != nil {
|
||||
return nil, fmt.Errorf("解析JSON数据失败: %w", err)
|
||||
}
|
||||
|
||||
// 转换为ProxyIP列表
|
||||
result := make([]ProxyIP, 0, len(ipList.IPs))
|
||||
for _, ip := range ipList.IPs {
|
||||
result = append(result, ProxyIP{
|
||||
IP: ip.IP,
|
||||
Protocol: "http",
|
||||
Ext: ip.Ext,
|
||||
})
|
||||
}
|
||||
|
||||
if len(result) == 0 {
|
||||
return nil, fmt.Errorf("API返回的IP列表为空")
|
||||
}
|
||||
|
||||
return result, nil
|
||||
}
|
||||
Reference in New Issue
Block a user