cloudagent-daemon 0.4.0__tar.gz → 0.4.1__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/PKG-INFO +1 -1
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/pyproject.toml +1 -1
- cloudagent_daemon-0.4.1/src/cloudagent_daemon/__init__.py +1 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/runtime_detect.py +7 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_runtime_detect.py +41 -0
- cloudagent_daemon-0.4.0/src/cloudagent_daemon/__init__.py +0 -1
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/.gitignore +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/LICENSE +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/README.md +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/__main__.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/agent_upload.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/agent_upload_denylist.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/claude_runner.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/cli.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/config.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/context_fetch.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/delegation_report.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/doctor.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/frame_dispatch.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/http_outbound.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/injection_state.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/jsonl_logging.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/login.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/main_loop.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/mcp_bridge.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/metrics.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/metrics_server.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/outbound_queue.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/paths.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/protocol.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/readonly_bash_guard.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/service.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/spawn_outbox.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/spawn_queue.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/sse_client.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/transport.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/unix_socket.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/workspace.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/ws_client.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/__init__.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/_fake_sse_server.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/conftest.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_e2e_deliver_to_spawn.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_e2e_sse.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_full_e2e.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_mcp_bridge_round_trip.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_one_shot_cli.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_spawn_mcp_bridge_e2e.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_sse_handshake.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_sse_watchdog.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_ws_handshake.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_ws_reconnect.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/conftest.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_agent_upload.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_claude_runner.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_claude_runner_codex_contract.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_claude_runner_routing_contract.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_claude_runner_w3.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_cli_multi_profile.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_cli_smoke.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_config.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_context_fetch.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_delegation_report.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_doctor.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_frame_dispatch.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_http_outbound.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_injection_state.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_jsonl_logging.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_login.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_main_loop_assign.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_mcp_bridge_agent_retrieval.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_mcp_bridge_send_message.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_metrics.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_metrics_server.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_multi_tool_wake.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_outbound_queue.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_outbox_stuck_watchdog.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_paths.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_protocol.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_readonly_bash_guard.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_service.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_service_multi_profile.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_spawn_outbox.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_spawn_queue.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_sse_active_watchdog.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_status_stop.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_workspace.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_workspace_root_task113.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_ws_client_insecure.py +0 -0
- {cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/uv.lock +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: cloudagent-daemon
|
|
3
|
-
Version: 0.4.
|
|
3
|
+
Version: 0.4.1
|
|
4
4
|
Summary: Local daemon for cloudagent — bridges Claude Code subprocesses to the cloudagent backend over WebSocket.
|
|
5
5
|
Project-URL: Homepage, https://cloudagent.chat
|
|
6
6
|
Project-URL: Repository, https://codeup.aliyun.com/69bd0a4d29ad98af4065ce71/cloudagent
|
|
@@ -4,7 +4,7 @@ build-backend = "hatchling.build"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "cloudagent-daemon"
|
|
7
|
-
version = "0.4.
|
|
7
|
+
version = "0.4.1"
|
|
8
8
|
description = "Local daemon for cloudagent — bridges Claude Code subprocesses to the cloudagent backend over WebSocket."
|
|
9
9
|
authors = [{name = "chaoyin", email = "tudoucyx@gmail.com"}]
|
|
10
10
|
readme = "README.md"
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
__version__ = "0.4.1"
|
|
@@ -123,6 +123,13 @@ def _capture_version(binary: str, args: list[str], timeout: float) -> str:
|
|
|
123
123
|
)
|
|
124
124
|
except (subprocess.TimeoutExpired, OSError):
|
|
125
125
|
return "unknown"
|
|
126
|
+
# 2026-07-23 (macpro Dex 排查) — 探针失败必须归 "unknown",不能把报错行
|
|
127
|
+
# 当版本:残缺的 nvm codex `--version` 以 rc=1 打出
|
|
128
|
+
# "Error: spawn ~/.nvm/versions/node/v22.22.2/lib/...",_version_sort_key
|
|
129
|
+
# 抽出路径里的 (22,22,2) 反而压过真 codex 的 (0,145,0),坏安装胜出、
|
|
130
|
+
# agent spawn 秒崩。退出码非零 = 不是可用的版本行。
|
|
131
|
+
if r.returncode != 0:
|
|
132
|
+
return "unknown"
|
|
126
133
|
out = (r.stdout or "") + (r.stderr or "")
|
|
127
134
|
first_line = out.strip().splitlines()[0] if out.strip() else ""
|
|
128
135
|
return first_line[:64] if first_line else "unknown"
|
|
@@ -273,3 +273,44 @@ class TestDetectRuntimes:
|
|
|
273
273
|
codex = next(r for r in result if r.name == "codex")
|
|
274
274
|
assert codex.version.startswith("v0.0.15")
|
|
275
275
|
assert str(new_node) in codex.binary
|
|
276
|
+
|
|
277
|
+
|
|
278
|
+
class TestBrokenInstallNeverWins:
|
|
279
|
+
"""2026-07-23 macpro Dex 排查回归:残缺安装的报错行不得冒充版本。
|
|
280
|
+
|
|
281
|
+
现场:nvm 里残缺的 codex `--version` 以 rc=1 打出
|
|
282
|
+
"Error: spawn ~/.nvm/versions/node/v22.22.2/lib/..."——
|
|
283
|
+
_version_sort_key 抽出 (22,22,2) 压过真 codex 的 (0,145,0),
|
|
284
|
+
坏安装胜出、agent spawn 秒崩。rc!=0 必须归 "unknown"。
|
|
285
|
+
"""
|
|
286
|
+
|
|
287
|
+
def test_nonzero_exit_probe_is_unknown(self, tmp_path, monkeypatch):
|
|
288
|
+
FakeBinary.write(
|
|
289
|
+
tmp_path, "codex",
|
|
290
|
+
stdout="Error: spawn /x/.nvm/versions/node/v22.22.2/lib/node",
|
|
291
|
+
exit_code=1,
|
|
292
|
+
)
|
|
293
|
+
monkeypatch.setattr("cloudagent_daemon.runtime_detect.shutil.which", lambda _: None)
|
|
294
|
+
monkeypatch.setenv("PATH", str(tmp_path))
|
|
295
|
+
result = detect_runtimes()
|
|
296
|
+
codex = [r for r in result if r.name == "codex"]
|
|
297
|
+
assert len(codex) == 1
|
|
298
|
+
assert codex[0].version == "unknown"
|
|
299
|
+
|
|
300
|
+
def test_healthy_low_version_beats_broken_high_digits(self, tmp_path, monkeypatch):
|
|
301
|
+
good_dir = tmp_path / "good"; good_dir.mkdir()
|
|
302
|
+
bad_dir = tmp_path / "bad"; bad_dir.mkdir()
|
|
303
|
+
FakeBinary.write(good_dir, "codex", stdout="codex-cli 0.145.0", exit_code=0)
|
|
304
|
+
FakeBinary.write(
|
|
305
|
+
bad_dir, "codex",
|
|
306
|
+
stdout="Error: spawn /x/.nvm/versions/node/v22.22.2/lib/node",
|
|
307
|
+
exit_code=1,
|
|
308
|
+
)
|
|
309
|
+
monkeypatch.setattr("cloudagent_daemon.runtime_detect.shutil.which", lambda _: None)
|
|
310
|
+
# 坏的排 PATH 前面 —— 修复后仍必须选到好的那份
|
|
311
|
+
monkeypatch.setenv("PATH", f"{bad_dir}{os.pathsep}{good_dir}")
|
|
312
|
+
result = detect_runtimes()
|
|
313
|
+
codex = [r for r in result if r.name == "codex"]
|
|
314
|
+
assert len(codex) == 1
|
|
315
|
+
assert codex[0].version.startswith("codex-cli 0.145.0")
|
|
316
|
+
assert str(good_dir) in codex[0].binary
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
__version__ = "0.4.0"
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/agent_upload_denylist.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/delegation_report.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/injection_state.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/src/cloudagent_daemon/readonly_bash_guard.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_e2e_deliver_to_spawn.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_mcp_bridge_round_trip.py
RENAMED
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/integration/test_spawn_mcp_bridge_e2e.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_claude_runner_codex_contract.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_mcp_bridge_agent_retrieval.py
RENAMED
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_mcp_bridge_send_message.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_outbox_stuck_watchdog.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_service_multi_profile.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cloudagent_daemon-0.4.0 → cloudagent_daemon-0.4.1}/tests/unit/test_workspace_root_task113.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|