From 8ced49a515b21b5be403fcff3f353d74c550244f Mon Sep 17 00:00:00 2001 From: iomgaa Date: Thu, 6 Aug 2026 05:16:53 -0400 Subject: [PATCH] chore: release 1.1.0 Minor rather than major: adding a parent class widens what an existing `except` catches, it does not break one. Callers already catching GovernanceBackendError keep working untouched. The wiki sync in the release checklist is a no-op this time. The doc site was taken down entirely on 2026-08-02 for accuracy reasons, and its remaining landing page points at CHANGELOG.md as the version source of truth, which this commit updates. --- CHANGELOG.md | 23 +++++++++++++++++++++++ pyproject.toml | 2 +- src/polygateway/__init__.py | 2 +- 3 files changed, 25 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index ff182ab..7268140 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,28 @@ # Changelog +## 1.1.0(2026-08-06) + +治理后端故障归位为 scope 级不可用(issue #7)。限流/熔断的状态后端(Redis 等)自身故障时,库按降级方向铁律 fail-closed——**整个 scope 一个请求都发不出去**,语义上就是"scope 级暂时不可用"。但 `GovernanceBackendError` 此前是 `PolyGatewayError` 的直接子类,只写 `except GatewayUnavailableError` 的调用方接不住,后果很具体: Redis 抖一下,积压任务一批批消耗业务失败预算,够到上限就进死信——**而那是运维重启一下就好的故障**。 + +### 行为变更(**请先读这一条**) + +- **`GovernanceBackendError` 现在能被 `except GatewayUnavailableError` 捕获。** 它改为继承该类,`reason` 恒为新增的 `governance_backend_down`。**下游对后端故障的处置路线因此改变**: 从"落进兜底分支、按业务失败处置"变为"按 scope 级不可用延期重投、不消耗失败预算"。这正是本次修复的目标,但升级前请确认下游的兜底分支没有依赖旧行为(例如靠它触发告警)。既有的 `except GovernanceBackendError` **继续有效**——加父类是扩大捕获面,不是破坏。 +- **配置写错(源名与限流后端配置不匹配)现在抛 `SourceNotConfiguredError` 而非 `GovernanceBackendError`。** 该类**有意不在** `GatewayUnavailableError` 之下: 那是装配缺陷不是暂时故障,必须消耗失败预算、进死信、让人看见。若随整类归入可重投家族,配置写错的任务会永远重投且无人告警——恰是本次要修的 bug 的镜像。 +- **`GovernanceBackendError` 的构造签名增加必填 keyword `scope`。** 库内 20 处构造点已全部更新;若下游有自行构造该异常的代码(罕见)需同步补 `scope`。 + +### 新增 + +- **`SourceNotConfiguredError`**(公共导出)。源名不在限流后端配置字典中时抛出,正常不可达,属装配缺陷。 +- **`GOVERNANCE_BACKEND_RETRY_AFTER_S = 5.0`**,`GovernanceBackendError.retry_after_s` 的默认值。**不是环境配置项**——后端恢复时间物理上不可知(不同于熔断冷却有确定到期时刻),故取保守固定值。**不取 0**: 那会让积压任务零延迟同时冲击已挂掉的后端,把一次故障放大成一场风暴。 +- **scope 级 `reason` 值域增 `governance_backend_down`**(由 5 值扩为 6 值)。 +- **README 新增"哪些异常会到达调用方"两列表**。四分类里 `TransientError` / `SourceDeadError` 被重试循环接住、耗尽时包成 `AllSourcesExhausted`,**根本到不了调用方**,而这只看类型树与 docstring 读不出来——曾让下游据此写错整段设计文档。 + +### 下游请读 + +- **`GovernanceBackendError` 现携带 `scope` / `reason` / `retry_after_s` / `per_source_reasons`**,与 `AllSourcesExhausted` 同款;`str(exc)` 仍是原来的诊断串(如 `限流后端 try_acquire 失败: ...`),结构化字段与诊断信息并存,排障不受影响。 +- **三条闸门路径**(`try_acquire` / `try_enter` / `progress_age_s`)的后端故障会到达调用方;记账路径(`record_success` 等)仍被 `_record_quietly` 降级为 warning,这个分工不变。 +- **CHSAnalyzer 迁移**: `tracking.py` 一条 `except GatewayUnavailableError` 即覆盖完整,无需为后端故障单列分支(`migrations/chsanalyzer.md` G1 已补注)。 + ## 1.0.6(2026-08-02) 推理开关能力建模与 `reasoning_tokens` 采集。`enable_thinking=False` 此前对 `minimax` / `openai` 两类源**完全不产生效果**——两个 profile 的 thinking 两档皆为空字典,`payload.update({})` 是空操作,而配置方以为关掉了推理。这比"不提供这个开关"更危险:不提供的话调用方会去找别的办法,提供了但静默失效,调用方就带着一个错误的前提往下走。一个下游项目正卡在这上面。 diff --git a/pyproject.toml b/pyproject.toml index 73aea52..a66968a 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta" [project] name = "polygateway" -version = "1.0.6" +version = "1.1.0" description = "PolyGateway:实验室统一的大语言模型(LLM/VLM/OCR)调度与中转库——多源、限流、重试、熔断、缓存、遥测" requires-python = ">=3.11" dependencies = [ diff --git a/src/polygateway/__init__.py b/src/polygateway/__init__.py index 56b26cf..19185ba 100644 --- a/src/polygateway/__init__.py +++ b/src/polygateway/__init__.py @@ -32,7 +32,7 @@ from polygateway.types import ( SourceConfig, ) -__version__ = "1.0.6" +__version__ = "1.1.0" __all__ = [ "DEFAULT_PROFILES",