fix: 9.5-code reachable items (parse unification, goal branch, fail-open logs, M7 test, fingerprint)
Parse: agent_tools/tool_approvals column parsing unified into agent_def shared helpers (parse None = undeclared; server keeps None, worker maps to []/{} at _task_from_row, dispatch behaviour unchanged). Goal: _apply_resume_preamble goal branch proven reachable via _goal_convert_queued on a queued auto-resumed task, kept with a test and corrected docs (not dead code). Fail-open: audit write failure and preamble lookup failure now log warnings (best-effort unchanged); partial policy failure and shadow parse drops documented as known gaps. M7: shadow endpoint explicit_capability_failures_truncated test. Fingerprint: RoutingPolicy.content_fingerprint (canonical JSON sha256, version excluded) surfaced only in dry-run output, never in audit rows. M1 wording: legacy gap stated as fixed stock persisting per-task until completion, not converging.
This commit is contained in:
1 parent
d95d678379
commit
1b8b6e525d
7 files changed
+498
-57
No files matched your search
@@ -414,6 +414,37 @@ class RoutingPolicy:
|
||||
"""Effective mode for one tier: explicit tier mode, else global."""
|
||||
return self.tier_modes.get(tier, self.mode)
|
||||
|
||||
def content_fingerprint(self):
|
||||
"""Content fingerprint of the parsed policy (9.5-code).
|
||||
|
||||
sha256 of the canonical JSON (sorted keys, tight
|
||||
separators) over the fields that decide routing and
|
||||
capability checks: mode, tiers, tier_modes,
|
||||
tier_requirements, model_capabilities, fallback_models.
|
||||
The operator-declared ``version`` string is deliberately
|
||||
NOT part of the fingerprint: it is hand-filled and may
|
||||
stay unchanged while requires change, so it cannot be
|
||||
trusted to detect a change. The fingerprint is only for
|
||||
dry-run output and debugging; it is never written into
|
||||
worker_routing audit rows, so the shadow parser (which
|
||||
splits audit detail on whitespace) is untouched.
|
||||
Two policies that parse to the same effective fields
|
||||
share a fingerprint even if their raw documents differ
|
||||
in key order or in dropped/invalid tiers.
|
||||
"""
|
||||
import hashlib
|
||||
payload = {
|
||||
"mode": self.mode,
|
||||
"tiers": self.tiers,
|
||||
"tier_modes": self.tier_modes,
|
||||
"tier_requirements": self.tier_requirements,
|
||||
"model_capabilities": self.model_capabilities,
|
||||
"fallback_models": self.fallback_models,
|
||||
}
|
||||
canonical = json.dumps(payload, sort_keys=True,
|
||||
separators=(",", ":"))
|
||||
return hashlib.sha256(canonical.encode("utf-8")).hexdigest()
|
||||
|
||||
|
||||
def parse_routing_policy(data):
|
||||
"""Parse one policy document, or return None when it is unusable.
|
||||
@@ -538,6 +569,15 @@ def load_routing_policy(env=None):
|
||||
" worker default", "; ".join(failures))
|
||||
return None
|
||||
if failures:
|
||||
# 9.5-code fail-open 清单:部分失败是 fail-open——
|
||||
# 可用来源继续生效、失败来源被丢弃,派发不炸。
|
||||
# 可见性只有这条警告日志:load_routing_policy 仍
|
||||
# 返回一个 policy,worker 的
|
||||
# routing_policy_load_failed 标志只在全失败时
|
||||
# 置位,所以部分失败不会产生任务级审计;运营方
|
||||
# 只能从 worker 日志看到它,不能从审计里查到。
|
||||
# 这是已知缺口(非静默,但不如全失败可见),
|
||||
# 改动返回类型会牵动全部调用方,本轨不改。
|
||||
_logger.warning(
|
||||
"routing policy partially failed (%s); continuing with"
|
||||
" the usable source", "; ".join(failures))
|
||||
|
||||
Reference in new issue
Block a user