refactor(llm-deepseek)!: rename the provider route to deepseek-official
The native adapter's route was named deepseek, colliding with pi-ai's catalog provider of the same name, so the two DeepSeek paths could never be mounted side by side. The web settings page needs both configurable at once. Compositions, fixtures, goldens, scaffolding defaults, and docs all move together (pre-release, no shim); TUI/session-query-spill/ missing-credential goldens re-recorded through their keyless refresh modes because provider-name length shifts box padding and spill truncation points.
This commit is contained in:
@@ -25,7 +25,7 @@ By default, the SDK launches the bundled single-file `dsh-jsonrpc-agent` executa
|
||||
from deepseek_harness import DeepSeekHarness
|
||||
|
||||
with DeepSeekHarness(
|
||||
provider="deepseek",
|
||||
provider="deepseek-official",
|
||||
model="deepseek-v4-flash",
|
||||
max_tokens=49_152,
|
||||
cordis="examples/jsonrpc-agent/cordis.yml",
|
||||
@@ -33,7 +33,7 @@ with DeepSeekHarness(
|
||||
result = harness.run("Make the requested code change.")
|
||||
```
|
||||
|
||||
`provider` selects a provider route registered by the chosen Cordis composition; `model` is the model id resolved by that adapter. `max_tokens` is an optional positive per-request output-token cap for the root agent and its in-process descendants; omission leaves the provider default in control. Compaction summaries keep the separate limit configured by their compaction plugin. The bundled default composition registers `deepseek`. A custom composition can mount `llm-pi-ai`, configure provider-specific credentials/endpoints there, and select any provider/model present in pi-ai's installed catalog.
|
||||
`provider` selects a provider route registered by the chosen Cordis composition; `model` is the model id resolved by that adapter. `max_tokens` is an optional positive per-request output-token cap for the root agent and its in-process descendants; omission leaves the provider default in control. Compaction summaries keep the separate limit configured by their compaction plugin. The bundled default composition registers `deepseek-official`. A custom composition can mount `llm-pi-ai`, configure provider-specific credentials/endpoints there, and select any provider/model present in pi-ai's installed catalog.
|
||||
|
||||
`HarnessClient` retains discovered subagent ancestry for the lifetime of the runtime process. During each `Session.run()`, `TurnResult.notifications` and `on_notification` receive the root session and all known descendant notifications in wire order, including nested subagent lifecycle and session events. `TurnResult.events` remains the root session's complete event stream, and `TurnResult.final_response` is the text content from its last `assistant/message`; descendant messages therefore cannot replace the root response.
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@ with DeepSeekHarness() as harness:
|
||||
from deepseek_harness import DeepSeekHarness
|
||||
|
||||
with DeepSeekHarness(
|
||||
provider="deepseek",
|
||||
provider="deepseek-official",
|
||||
model="deepseek-v4-flash",
|
||||
max_tokens=49_152,
|
||||
cordis="examples/jsonrpc-agent/cordis.yml",
|
||||
@@ -29,7 +29,7 @@ with DeepSeekHarness(
|
||||
result = harness.run("Make the requested code change.")
|
||||
```
|
||||
|
||||
`provider` 用于选择当前 Cordis 组合已注册的提供方路由;`model` 是该适配器解析的模型 ID。`max_tokens` 是可选的正整数,用于限制根 agent 及其进程内后代每次请求的输出 token;省略时由提供方默认值控制。压缩摘要继续使用压缩插件单独配置的上限。内置默认组合注册 `deepseek`。自定义组合可以挂载 `llm-pi-ai`,在其中配置各提供方的凭据与端点,再选择 pi-ai 已安装目录中的任意提供方/模型组合。
|
||||
`provider` 用于选择当前 Cordis 组合已注册的提供方路由;`model` 是该适配器解析的模型 ID。`max_tokens` 是可选的正整数,用于限制根 agent 及其进程内后代每次请求的输出 token;省略时由提供方默认值控制。压缩摘要继续使用压缩插件单独配置的上限。内置默认组合注册 `deepseek-official`。自定义组合可以挂载 `llm-pi-ai`,在其中配置各提供方的凭据与端点,再选择 pi-ai 已安装目录中的任意提供方/模型组合。
|
||||
|
||||
`HarnessClient` 会在运行时进程的生命周期内保留已发现的 subagent(子 agent)祖先关系。每次执行 `Session.run()` 时,`TurnResult.notifications` 与 `on_notification` 会按线上的原始顺序收到根会话及所有已知后代的通知,其中包括嵌套 subagent 的生命周期与会话事件。`TurnResult.events` 仍只保存根会话的完整事件流,`TurnResult.final_response` 则取该会话最后一个 `assistant/message` 的文本内容,因此后代消息不会覆盖根会话回复。
|
||||
|
||||
|
||||
@@ -18,7 +18,7 @@ class DeepSeekHarnessConfig:
|
||||
intentionally override or inject variables for a subprocess.
|
||||
"""
|
||||
|
||||
provider: str = "deepseek"
|
||||
provider: str = "deepseek-official"
|
||||
model: str = "deepseek-v4-flash"
|
||||
max_tokens: int | None = None
|
||||
cwd: str | None = None
|
||||
|
||||
@@ -72,7 +72,7 @@ def test_bundled_runtime_boots_a_cordis_config(tmp_path: Path, mode: str) -> Non
|
||||
(tmp_path / "cordis.yml").write_text(_CORDIS_YML)
|
||||
|
||||
with _client(tmp_path, launch_args) as client:
|
||||
init = client.initialize(provider="deepseek", cwd=str(tmp_path), model="deepseek-v4-pro")
|
||||
init = client.initialize(provider="deepseek-official", cwd=str(tmp_path), model="deepseek-v4-pro")
|
||||
|
||||
assert init.serverInfo is not None
|
||||
assert init.serverInfo.name == "deepseek-harness-sdk-runtime"
|
||||
@@ -89,7 +89,7 @@ def test_bundled_runtime_surfaces_unbundled_plugin_failure(tmp_path: Path, mode:
|
||||
client.start()
|
||||
try:
|
||||
with pytest.raises((TransportClosedError, TimeoutError)) as excinfo:
|
||||
client.initialize(provider="deepseek", cwd=str(tmp_path), model="deepseek-v4-pro")
|
||||
client.initialize(provider="deepseek-official", cwd=str(tmp_path), model="deepseek-v4-pro")
|
||||
finally:
|
||||
client.close()
|
||||
|
||||
|
||||
@@ -89,7 +89,7 @@ for line in sys.stdin:
|
||||
assert dumped_env["DSH_CORDIS_CONFIG"] == str(tmp_path / "cordis.yml")
|
||||
assert json.loads(init_dump.read_text()) == {
|
||||
"cwd": str(tmp_path),
|
||||
"provider": "deepseek",
|
||||
"provider": "deepseek-official",
|
||||
"model": "deepseek-v4-flash",
|
||||
"maxTokens": 4096,
|
||||
}
|
||||
@@ -399,7 +399,7 @@ for line in sys.stdin:
|
||||
with HarnessClient(
|
||||
HarnessConfig(launch_args_override=(sys.executable, str(script)))
|
||||
) as client:
|
||||
init = client.initialize(provider="deepseek", cwd="/workspace", model="dsagent")
|
||||
init = client.initialize(provider="deepseek-official", cwd="/workspace", model="dsagent")
|
||||
assert init.serverInfo.name == "fake-dsh"
|
||||
|
||||
client.session_prompt("main", [{"type": "text", "text": "fix it"}])
|
||||
@@ -537,7 +537,7 @@ for line in sys.stdin:
|
||||
raise RuntimeError("bad notification filter")
|
||||
|
||||
with HarnessClient(HarnessConfig(launch_args_override=(sys.executable, str(script)))) as client:
|
||||
client.initialize(provider="deepseek", cwd="/workspace", model="dsagent")
|
||||
client.initialize(provider="deepseek-official", cwd="/workspace", model="dsagent")
|
||||
with (
|
||||
client.subscribe_notifications(broken_filter) as broken,
|
||||
client.subscribe_notifications(lambda notification: notification.method == "tick") as healthy,
|
||||
@@ -574,7 +574,7 @@ for line in sys.stdin:
|
||||
)
|
||||
|
||||
with HarnessClient(HarnessConfig(launch_args_override=(sys.executable, str(script)))) as client:
|
||||
client.initialize(provider="deepseek", cwd="/workspace", model="dsagent")
|
||||
client.initialize(provider="deepseek-official", cwd="/workspace", model="dsagent")
|
||||
with pytest.raises(ValueError):
|
||||
client.session_prompt("main", [{"type": "text", "text": "fix it"}])
|
||||
|
||||
@@ -603,7 +603,7 @@ for line in sys.stdin:
|
||||
with HarnessClient(
|
||||
HarnessConfig(launch_args_override=(sys.executable, str(script)))
|
||||
) as client:
|
||||
client.initialize(provider="deepseek", cwd="/workspace", model="dsagent")
|
||||
client.initialize(provider="deepseek-official", cwd="/workspace", model="dsagent")
|
||||
|
||||
request = client.next_request()
|
||||
assert request.id == "bridge-req-1"
|
||||
@@ -637,7 +637,7 @@ for line in sys.stdin:
|
||||
with HarnessClient(
|
||||
HarnessConfig(launch_args_override=(sys.executable, str(script)))
|
||||
) as client:
|
||||
init = client.initialize(provider="deepseek", cwd="/workspace", model="dsagent")
|
||||
init = client.initialize(provider="deepseek-official", cwd="/workspace", model="dsagent")
|
||||
assert init.serverInfo.name == "fake-dsh"
|
||||
|
||||
|
||||
@@ -659,7 +659,7 @@ time.sleep(60)
|
||||
) as client:
|
||||
start = time.monotonic()
|
||||
try:
|
||||
client.initialize(provider="deepseek", cwd="/workspace", model="dsagent")
|
||||
client.initialize(provider="deepseek-official", cwd="/workspace", model="dsagent")
|
||||
except TimeoutError:
|
||||
assert time.monotonic() - start < 2
|
||||
else:
|
||||
@@ -695,7 +695,7 @@ for line in sys.stdin:
|
||||
client.start()
|
||||
proc = client._proc
|
||||
assert proc is not None
|
||||
client.initialize(provider="deepseek", cwd="/workspace", model="dsagent")
|
||||
client.initialize(provider="deepseek-official", cwd="/workspace", model="dsagent")
|
||||
start = time.monotonic()
|
||||
client.close()
|
||||
assert time.monotonic() - start < 2
|
||||
@@ -726,7 +726,7 @@ for line in sys.stdin:
|
||||
assert proc is not None
|
||||
|
||||
with pytest.raises(Exception, match="bad initialize"):
|
||||
client.initialize(provider="deepseek", cwd=".", model="dsagent")
|
||||
client.initialize(provider="deepseek-official", cwd=".", model="dsagent")
|
||||
|
||||
assert proc.wait(timeout=1) is not None
|
||||
assert client._proc is None
|
||||
@@ -768,7 +768,7 @@ for line in sys.stdin:
|
||||
|
||||
client = HarnessClient(HarnessConfig(launch_args_override=(sys.executable, str(script))))
|
||||
client.start()
|
||||
client.initialize(provider="deepseek", cwd="/workspace", model="dsagent")
|
||||
client.initialize(provider="deepseek-official", cwd="/workspace", model="dsagent")
|
||||
client.close()
|
||||
client.close()
|
||||
|
||||
@@ -791,7 +791,7 @@ sys.exit(42)
|
||||
)
|
||||
) as client:
|
||||
with pytest.raises(Exception, match="fatal bridge exploded"):
|
||||
client.initialize(provider="deepseek", cwd="/workspace", model="dsagent")
|
||||
client.initialize(provider="deepseek-official", cwd="/workspace", model="dsagent")
|
||||
|
||||
|
||||
def test_client_serializes_concurrent_writes(tmp_path: Path) -> None:
|
||||
@@ -822,7 +822,7 @@ with open(os.environ["SEEN"], "w") as seen:
|
||||
env={"SEEN": str(output)},
|
||||
)
|
||||
) as client:
|
||||
client.initialize(provider="deepseek", cwd="/workspace", model="dsagent")
|
||||
client.initialize(provider="deepseek-official", cwd="/workspace", model="dsagent")
|
||||
threads = [
|
||||
threading.Thread(target=client.notify, args=(f"notice-{index}", {"index": index}))
|
||||
for index in range(50)
|
||||
@@ -893,7 +893,7 @@ def test_client_default_launch_uses_bundled_runtime_and_injects_default_config(
|
||||
monkeypatch.setenv("DSH_CORDIS_CONFIG", ambient_config)
|
||||
|
||||
with HarnessClient(HarnessConfig(env={"ENV_DUMP": str(env_dump)})) as client:
|
||||
init = client.initialize(provider="deepseek", cwd="/workspace", model="deepseek-v4-pro")
|
||||
init = client.initialize(provider="deepseek-official", cwd="/workspace", model="deepseek-v4-pro")
|
||||
|
||||
assert init.serverInfo.name == "bundled-runtime"
|
||||
assert json.loads(env_dump.read_text())["DSH_CORDIS_CONFIG"] == str(default_config)
|
||||
@@ -909,7 +909,7 @@ def test_client_respects_explicit_config_over_bundled_default(
|
||||
with HarnessClient(
|
||||
HarnessConfig(env={"ENV_DUMP": str(env_dump), "DSH_CORDIS_CONFIG": "./explicit.yml"})
|
||||
) as client:
|
||||
client.initialize(provider="deepseek", cwd="/workspace", model="deepseek-v4-pro")
|
||||
client.initialize(provider="deepseek-official", cwd="/workspace", model="deepseek-v4-pro")
|
||||
|
||||
assert json.loads(env_dump.read_text())["DSH_CORDIS_CONFIG"] == "./explicit.yml"
|
||||
|
||||
|
||||
Reference in New Issue
Block a user