复刻 @nodeagent/client 的协议行为,供桌面控制台(Tauri 壳)经 Cargo path 依赖: - 模块:error / types / ulid / crypto / tls / discovery / client - 握手:hello → challenge → auth → auth_ok;psk(HMAC-SHA256) 与 ed25519 两种模式 - 证书指纹 sha256(DER) 钉住(E_CERT_MISMATCH);ULID(Crockford Base32) - 断线指数退避重连 1s→30s(±15% 抖动) Rust async Send 三层陷阱(本轮主要成本,解法已写入 client.rs 注释): 1. futures_util::lock::Mutex 无手写 Sync 实现 → 含它的类型整体 !Sync 2. tokio::sync::MutexGuard 非 Send 3. establish → spawn(read_loop) → on_disconnected → establish 构成**类型级递归**, 编译器无法证明 Send。最终采用**监督者模式**:单个 supervise 任务串行 「建立+握手 → 等读循环 Notify 断开 → 退避重连」,读循环只 notify 不回调 establish,从而打破递归;发送半用专用写任务 + mpsc 解耦(同步 send,不跨 await 持锁)。 测试:9 单测(crypto/ulid/Send+Sync 断言)+ 2 E2E(psk 握手→invoke 全链路、连不上端口 返回 NODE_OFFLINE),`cargo clippy --all-targets -- -D warnings` 零告警。 另附 examples/connect.rs(连真实被控端)与 examples/probe.rs(字段契约探针, 输出顶层键+数组首元素键,并按 system.info.os 区分「平台不支持」与「真失败」)。 .gitignore:crates/ 转正后必须显式忽略 /crates/target/ —— 此前是靠整个 /crates/ 被忽略才没让 4GB 级构建产物进库,取消那条保护后会裸奔。
24 lines
719 B
TOML
24 lines
719 B
TOML
[package]
|
||
name = "nodeagent-client"
|
||
version = "0.1.0"
|
||
edition = "2021"
|
||
description = "nodeagent 控制端 Rust 客户端(行为对齐 @nodeagent/client)"
|
||
license = "MIT"
|
||
|
||
[dependencies]
|
||
base64 = "0.23.1"
|
||
ed25519-dalek = { version = "3.0.0", features = ["pkcs8", "alloc"] }
|
||
futures-util = "0.3.34"
|
||
hmac = "0.13.0"
|
||
rand = "0.10.3"
|
||
rustls = "0.23.45"
|
||
rustls-pemfile = "2.2.0"
|
||
serde = { version = "1.0.229", features = ["derive"] }
|
||
serde_json = "1.0.151"
|
||
sha2 = "0.11.0"
|
||
thiserror = "2.0.21"
|
||
tokio = { version = "1.53.2", features = ["rt-multi-thread", "net", "time", "sync", "macros", "io-util"] }
|
||
tokio-tungstenite = { version = "0.30.0", features = ["rustls-tls-webpki-roots"] }
|
||
url = "2.5.8"
|
||
webpki-roots = "1.0.9"
|