192 lines
5.9 KiB
Python
Executable File
192 lines
5.9 KiB
Python
Executable File
#!/usr/bin/env python3
|
|
"""
|
|
Webshare 代理管理器
|
|
通过 Tailscale 连接甲骨文节点进行代理中转
|
|
"""
|
|
|
|
import subprocess
|
|
import time
|
|
import threading
|
|
import json
|
|
import requests
|
|
from concurrent.futures import ThreadPoolExecutor
|
|
|
|
class ProxyManager:
|
|
def __init__(self, oracle_ip):
|
|
self.oracle_ip = oracle_ip
|
|
self.local_start_port = 20001
|
|
self.oracle_start_port = 10001
|
|
self.proxy_count = 20
|
|
self.processes = []
|
|
|
|
def start_local_forwards(self):
|
|
"""启动本地转发"""
|
|
print(f"启动本地代理转发到甲骨文服务器 {self.oracle_ip}")
|
|
|
|
# 清理之前的进程
|
|
self.stop_forwards()
|
|
|
|
for i in range(self.proxy_count):
|
|
local_port = self.local_start_port + i
|
|
oracle_port = self.oracle_start_port + i
|
|
|
|
cmd = [
|
|
'gost',
|
|
'-L', f'socks5://127.0.0.1:{local_port}',
|
|
'-F', f'socks5://{self.oracle_ip}:{oracle_port}'
|
|
]
|
|
|
|
try:
|
|
process = subprocess.Popen(cmd, stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL)
|
|
self.processes.append(process)
|
|
print(f"本地端口 {local_port} -> 甲骨文 {self.oracle_ip}:{oracle_port}")
|
|
time.sleep(0.1)
|
|
except Exception as e:
|
|
print(f"启动转发失败 {local_port}: {e}")
|
|
|
|
print(f"已启动 {len(self.processes)} 个代理转发")
|
|
|
|
def stop_forwards(self):
|
|
"""停止所有转发"""
|
|
for process in self.processes:
|
|
try:
|
|
process.terminate()
|
|
process.wait(timeout=5)
|
|
except:
|
|
try:
|
|
process.kill()
|
|
except:
|
|
pass
|
|
self.processes.clear()
|
|
|
|
# 额外清理
|
|
try:
|
|
subprocess.run(['pkill', '-f', 'gost.*:2000'], check=False)
|
|
except:
|
|
pass
|
|
|
|
def test_proxy(self, port):
|
|
"""测试单个代理"""
|
|
try:
|
|
proxy = f'socks5://127.0.0.1:{port}'
|
|
response = requests.get(
|
|
'http://httpbin.org/ip',
|
|
proxies={'http': proxy, 'https': proxy},
|
|
timeout=10
|
|
)
|
|
if response.status_code == 200:
|
|
ip = response.json().get('origin', 'Unknown')
|
|
return port, True, ip
|
|
except Exception as e:
|
|
return port, False, str(e)
|
|
return port, False, 'Timeout'
|
|
|
|
def test_all_proxies(self):
|
|
"""测试所有代理"""
|
|
print("测试代理连接...")
|
|
ports = [self.local_start_port + i for i in range(self.proxy_count)]
|
|
|
|
with ThreadPoolExecutor(max_workers=10) as executor:
|
|
results = list(executor.map(self.test_proxy, ports))
|
|
|
|
working = 0
|
|
failed = 0
|
|
|
|
for port, success, info in results:
|
|
if success:
|
|
print(f"✓ 端口 {port}: {info}")
|
|
working += 1
|
|
else:
|
|
print(f"✗ 端口 {port}: {info}")
|
|
failed += 1
|
|
|
|
print(f"\n测试结果: {working} 个工作, {failed} 个失败")
|
|
return working, failed
|
|
|
|
def generate_clash_config(self):
|
|
"""生成 Clash 配置"""
|
|
config = {
|
|
'port': 7890,
|
|
'socks-port': 7891,
|
|
'allow-lan': True,
|
|
'mode': 'Rule',
|
|
'log-level': 'info',
|
|
'external-controller': '127.0.0.1:9090',
|
|
'proxies': [],
|
|
'proxy-groups': [],
|
|
'rules': ['MATCH,WebShare']
|
|
}
|
|
|
|
# 添加代理
|
|
for i in range(self.proxy_count):
|
|
port = self.local_start_port + i
|
|
config['proxies'].append({
|
|
'name': f'WebShare-{i+1}',
|
|
'type': 'socks5',
|
|
'server': '127.0.0.1',
|
|
'port': port
|
|
})
|
|
|
|
# 选择组
|
|
proxy_names = [f'WebShare-{i+1}' for i in range(self.proxy_count)]
|
|
config['proxy-groups'].append({
|
|
'name': 'WebShare',
|
|
'type': 'select',
|
|
'proxies': proxy_names
|
|
})
|
|
|
|
# 负载均衡组
|
|
config['proxy-groups'].append({
|
|
'name': 'LoadBalance',
|
|
'type': 'load-balance',
|
|
'url': 'http://www.gstatic.com/generate_204',
|
|
'interval': 300,
|
|
'proxies': proxy_names
|
|
})
|
|
|
|
# 保存配置
|
|
with open('clash-webshare-auto.yaml', 'w') as f:
|
|
import yaml
|
|
yaml.dump(config, f, default_flow_style=False)
|
|
|
|
print("Clash 配置已生成: clash-webshare-auto.yaml")
|
|
|
|
def run(self):
|
|
"""运行管理器"""
|
|
try:
|
|
self.start_local_forwards()
|
|
time.sleep(2) # 等待连接建立
|
|
|
|
working, failed = self.test_all_proxies()
|
|
|
|
if working > 0:
|
|
self.generate_clash_config()
|
|
print(f"\n可用代理端口: 127.0.0.1:{self.local_start_port}-{self.local_start_port + working - 1}")
|
|
print("\n按 Ctrl+C 停止...")
|
|
|
|
while True:
|
|
time.sleep(60)
|
|
# 定期检查
|
|
print(".", end="", flush=True)
|
|
else:
|
|
print("没有可用的代理连接")
|
|
|
|
except KeyboardInterrupt:
|
|
print("\n正在停止...")
|
|
finally:
|
|
self.stop_forwards()
|
|
|
|
def main():
|
|
import sys
|
|
|
|
if len(sys.argv) != 2:
|
|
print("使用方法: python3 proxy-manager.py <甲骨文Tailscale IP>")
|
|
print("示例: python3 proxy-manager.py 100.64.0.1")
|
|
sys.exit(1)
|
|
|
|
oracle_ip = sys.argv[1]
|
|
manager = ProxyManager(oracle_ip)
|
|
manager.run()
|
|
|
|
if __name__ == "__main__":
|
|
main() |