mirror of
https://github.com/fawney19/Aether.git
synced 2026-09-03 01:40:21 +08:00
feat(provider): 增加 Claude Code 适配器、高级配置能力与 OAuth 账号类型统一解析
- 新增 Claude Code provider adapter (context, envelope, plugin, constants) - 扩展 provider admin 路由,支持 Claude Code 高级配置 (CRUD) - 统一 OAuth 账号类型解析逻辑,前后端对齐 - 重构 BatchAssignModelsDialog / ModelMappingDialog,简化组件逻辑 - handler 基类增强: request_builder 支持 Claude Code 信封格式 - CLI stream/sync mixin 适配 Claude Code 流式与同步模式 - 扩展 candidate builder / failover / scheduler 对 Claude Code 的支持 - 前端增加请求时间线可视化 (HorizontalRequestTimeline) - 补充 Claude Code envelope / runtime controls / distributed sessions 等测试 Closes #183 Closes #185 Co-Authored-By: AAEE86 <ppk0227@hotmail.com>
This commit is contained in:
@@ -25,7 +25,7 @@ from src.services.proxy_node.resolver import (
|
||||
get_system_proxy_config,
|
||||
make_proxy_param,
|
||||
)
|
||||
from src.utils.ssl_utils import get_ssl_context
|
||||
from src.utils.ssl_utils import get_ssl_context, get_ssl_context_for_profile
|
||||
|
||||
# 模块级锁,避免类属性延迟初始化的竞态条件
|
||||
_proxy_clients_lock = asyncio.Lock()
|
||||
@@ -186,6 +186,7 @@ class HTTPClientPool:
|
||||
async def get_proxy_client(
|
||||
cls,
|
||||
proxy_config: dict[str, Any] | None = None,
|
||||
tls_profile: str | None = None,
|
||||
) -> httpx.AsyncClient:
|
||||
"""
|
||||
获取代理客户端(带缓存复用)
|
||||
@@ -212,6 +213,9 @@ class HTTPClientPool:
|
||||
return await cls._get_tunnel_client(delegate_cfg["node_id"])
|
||||
|
||||
cache_key = compute_proxy_cache_key(proxy_config)
|
||||
tls_profile_key = str(tls_profile or "").strip().lower()
|
||||
if tls_profile_key:
|
||||
cache_key = f"{cache_key}::tls:{tls_profile_key}"
|
||||
|
||||
# 无代理时返回默认客户端
|
||||
if cache_key == "__no_proxy__":
|
||||
@@ -229,6 +233,10 @@ class HTTPClientPool:
|
||||
else:
|
||||
# 更新最后使用时间
|
||||
cls._proxy_clients[cache_key] = (client, time.time())
|
||||
if tls_profile_key:
|
||||
logger.debug(
|
||||
"复用代理客户端 TLS profile={} key={}", tls_profile_key, cache_key
|
||||
)
|
||||
return client
|
||||
|
||||
# 淘汰旧客户端(如果超过上限)
|
||||
@@ -237,7 +245,7 @@ class HTTPClientPool:
|
||||
# 创建新客户端(使用默认超时,请求时可覆盖)
|
||||
client_config: dict[str, Any] = {
|
||||
"http2": False,
|
||||
"verify": get_ssl_context(),
|
||||
"verify": get_ssl_context_for_profile(tls_profile),
|
||||
"follow_redirects": True,
|
||||
"limits": httpx.Limits(
|
||||
max_connections=config.http_max_connections,
|
||||
@@ -269,6 +277,8 @@ class HTTPClientPool:
|
||||
logger.debug(
|
||||
"创建代理客户端(缓存): {}, 缓存数量: {}", proxy_label, len(cls._proxy_clients)
|
||||
)
|
||||
if tls_profile_key:
|
||||
logger.debug("创建代理客户端 TLS profile={} key={}", tls_profile_key, cache_key)
|
||||
|
||||
return client
|
||||
|
||||
@@ -342,6 +352,7 @@ class HTTPClientPool:
|
||||
cls,
|
||||
proxy_config: dict[str, Any] | None = None,
|
||||
timeout: httpx.Timeout | None = None,
|
||||
tls_profile: str | None = None,
|
||||
**kwargs: Any,
|
||||
) -> httpx.AsyncClient:
|
||||
"""
|
||||
@@ -359,7 +370,7 @@ class HTTPClientPool:
|
||||
"""
|
||||
client_config: dict[str, Any] = {
|
||||
"http2": False,
|
||||
"verify": get_ssl_context(),
|
||||
"verify": get_ssl_context_for_profile(tls_profile),
|
||||
"follow_redirects": True,
|
||||
}
|
||||
|
||||
@@ -392,6 +403,7 @@ class HTTPClientPool:
|
||||
cls,
|
||||
delegate_cfg: dict[str, Any] | None,
|
||||
proxy_config: dict[str, Any] | None = None,
|
||||
tls_profile: str | None = None,
|
||||
) -> httpx.AsyncClient:
|
||||
"""
|
||||
获取可复用的上游请求客户端(自动选择 tunnel/代理模式)
|
||||
@@ -401,7 +413,7 @@ class HTTPClientPool:
|
||||
"""
|
||||
if delegate_cfg and delegate_cfg.get("tunnel"):
|
||||
return await cls._get_tunnel_client(delegate_cfg["node_id"])
|
||||
return await cls.get_proxy_client(proxy_config=proxy_config)
|
||||
return await cls.get_proxy_client(proxy_config=proxy_config, tls_profile=tls_profile)
|
||||
|
||||
@classmethod
|
||||
async def create_upstream_stream_client(
|
||||
@@ -409,6 +421,7 @@ class HTTPClientPool:
|
||||
delegate_cfg: dict[str, Any] | None,
|
||||
proxy_config: dict[str, Any] | None = None,
|
||||
timeout: httpx.Timeout | None = None,
|
||||
tls_profile: str | None = None,
|
||||
) -> httpx.AsyncClient:
|
||||
"""
|
||||
创建上游流式请求客户端(自动选择 tunnel/代理模式)
|
||||
@@ -417,7 +430,11 @@ class HTTPClientPool:
|
||||
"""
|
||||
if delegate_cfg and delegate_cfg.get("tunnel"):
|
||||
return await cls._get_tunnel_client(delegate_cfg["node_id"], timeout=timeout)
|
||||
return cls.create_client_with_proxy(proxy_config=proxy_config, timeout=timeout)
|
||||
return cls.create_client_with_proxy(
|
||||
proxy_config=proxy_config,
|
||||
timeout=timeout,
|
||||
tls_profile=tls_profile,
|
||||
)
|
||||
|
||||
@classmethod
|
||||
async def _get_tunnel_client(
|
||||
|
||||
Reference in New Issue
Block a user