feat: 性能监控基础设施、解密缓存及计费简化

- 新增 PerfRecorder 性能记录工具,支持采样率与慢请求日志
- 在请求管道中埋点:auth、body_read、json_parse、context_build、authorize、handle
- 流处理器增加 parse/conversion 耗时追踪与 perf_metrics 落库
- 解密服务添加 LRU 缓存,降低高频解密 CPU 开销
- 格式转换分层开关设计:全局 OFF 时回退到端点配置,而非一刀切拒绝
- 移除 shadow billing 模块,统一使用新计费引擎
- 新增 Codex 网关请求适配器(store=false、role 映射、include 补齐)
- endpoint 创建接口支持 body_rules 参数
This commit is contained in:
fawney19
2026-02-05 14:22:11 +08:00
parent e72e5370c4
commit ed2ff5c1d7
25 changed files with 836 additions and 963 deletions

View File

@@ -67,7 +67,11 @@ async def test_build_candidates_allows_cross_format_when_endpoint_accepts_and_ov
@pytest.mark.asyncio
async def test_build_candidates_blocks_cross_format_when_master_switch_off() -> None:
async def test_build_candidates_allows_cross_format_when_global_off_but_endpoint_enabled() -> None:
"""
分层开关设计:全局 OFF 时回退到端点配置
- 全局 OFF + 端点 enabled=True -> 允许(端点覆盖全局默认)
"""
register_default_normalizers()
scheduler = CacheAwareScheduler()
@@ -85,6 +89,40 @@ async def test_build_candidates_blocks_cross_format_when_master_switch_off() ->
]
provider.api_keys = [_mock_key("k1", ["openai:chat"])]
candidates = await scheduler._build_candidates(
db=MagicMock(),
providers=[provider],
client_format="claude:chat",
model_name="dummy-model",
affinity_key=None,
global_conversion_enabled=False, # 全局开关关闭,但端点配置允许
)
# 新设计:全局 OFF 时回退到端点配置,端点 enabled=True 则允许
assert len(candidates) == 1
assert candidates[0].needs_conversion is True
assert candidates[0].provider_api_format == "openai:chat"
@pytest.mark.asyncio
async def test_build_candidates_blocks_cross_format_when_global_off_and_endpoint_not_configured() -> (
None
):
"""
分层开关设计:全局 OFF + 端点未配置 -> 阻止
"""
register_default_normalizers()
scheduler = CacheAwareScheduler()
scheduler._check_model_support = AsyncMock(return_value=(True, None, None, {"m"})) # type: ignore[method-assign]
scheduler._check_key_availability = MagicMock(return_value=(True, None, None)) # type: ignore[method-assign]
provider = MagicMock()
provider.name = "p1"
provider.enable_format_conversion = False
provider.endpoints = [_mock_endpoint("openai:chat", None)] # 端点未配置格式接受策略
provider.api_keys = [_mock_key("k1", ["openai:chat"])]
candidates = await scheduler._build_candidates(
db=MagicMock(),
providers=[provider],
@@ -94,6 +132,7 @@ async def test_build_candidates_blocks_cross_format_when_master_switch_off() ->
global_conversion_enabled=False, # 全局开关关闭
)
# 全局 OFF + 端点未配置 -> 阻止
assert candidates == []