feat: accept sampling overlay on chat() and per-source extra_body

Priority is structured injection > per-call overlay > per-source config,
and extra_body now takes part in the cache fingerprint.
This commit is contained in:
2026-07-31 21:17:49 -04:00
parent 152fa264ed
commit 6bb64ca938
4 changed files with 167 additions and 5 deletions
+21
View File
@@ -445,6 +445,27 @@ class TestRequestShaping:
)
assert seen["response_format"] == {"type": "json_object"}
async def test_extra_body_merged_and_outranked_by_overlay(self):
"""顺序即优先级: thinking profile → extra_body → overlay(issue #4)。"""
seen = {}
def handler(request):
seen.update(json.loads(request.content))
return _sse_stream(_chunk(content="x"), _chunk(usage=_USAGE))
await _complete(
_transport_for(handler),
_source(extra_body={"temperature": 0, "top_p": 0.9}),
overlay={"temperature": 1},
)
assert seen["temperature"] == 1 # 调用级覆盖配置级
assert seen["top_p"] == 0.9 # 未被顶掉的配置级键保留
async def test_extra_body_cannot_break_governed_keys(self):
"""治理键由 payload 骨架拥有;extra_body 的保护键在构造期已被拦下。"""
with pytest.raises(ValueError, match="stream"):
_source(extra_body={"stream": False})
class TestErrorTranslation:
@pytest.mark.parametrize(